Udostępnij za pośrednictwem


Struktury i pojęcia dotyczące strumienia węzłów XAML

Czytniki XAML i składniki zapisywania XAML implementowane w usługach XAML platformy .NET są oparte na koncepcji projektowania strumienia węzła XAML. Strumień węzła XAML to koncepcyjna koncepcja zestawu węzłów XAML. W tej koncepcji procesor XAML przechodzi przez strukturę relacji węzłów w języku XAML pojedynczo. W dowolnym momencie w otwartym strumieniu węzła XAML istnieje tylko jeden bieżący rekord lub bieżąca pozycja, a wiele aspektów raportu interfejsu API zawiera tylko informacje dostępne z tej pozycji. Bieżący węzeł w strumieniu węzła XAML można opisać jako obiekt, element członkowski lub wartość. Traktując język XAML jako strumień węzła XAML, czytelnicy XAML mogą komunikować się z składnikami zapisywania XAML i umożliwić programowi wyświetlanie, interakcję lub zmienianie zawartości strumienia węzła XAML podczas ścieżki ładowania lub operacji zapisywania ścieżki, która obejmuje XAML. Projekt interfejsu API czytnika i modułu zapisywania XAML oraz koncepcja strumienia węzłów XAML są podobne do poprzednich projektów i koncepcji czytelników i składników zapisywania, takich jak XML Document Object Model (DOM) oraz klasy XmlReader i XmlWriter. W tym temacie omówiono pojęcia dotyczące strumienia węzłów XAML i opisano sposób pisania procedur, które współdziałają z reprezentacjami XAML na poziomie węzła XAML.

Ładowanie kodu XAML do czytnika XAML

Klasa podstawowa XamlReader nie deklaruje określonej techniki ładowania początkowego kodu XAML do czytnika XAML. Zamiast tego klasa pochodna deklaruje i implementuje technikę ładowania, w tym ogólne cechy i ograniczenia źródła danych wejściowych dla języka XAML. Na przykład XamlObjectReader odczytuje wykres obiektu, zaczynając od źródła wejściowego pojedynczego obiektu, który reprezentuje element główny lub podstawowy. Następnie XamlObjectReader generuje strumień węzła XAML z grafu obiektów.

Najbardziej widoczną podklasą zdefiniowaną XamlReader usług XAML platformy .NET jest XamlXmlReader. XamlXmlReader ładuje początkowy kod XAML, ładując plik tekstowy bezpośrednio za pośrednictwem strumienia lub ścieżki pliku albo pośrednio za pośrednictwem powiązanej klasy czytnika, takiej jak TextReader. XamlReader można traktować jako zawierającą całe źródło danych wejściowych XAML po załadowaniu. Jednak podstawowy interfejs API XamlReader jest zaprojektowany tak, aby czytelnik wchodził w interakcję z jednym węzłem XAML. Po pierwszym załadowaniu pierwszy napotkany pojedynczy węzeł jest katalogiem głównym kodu XAML i jego obiektem początkowym.

Koncepcja strumienia węzła XAML

Jeśli znasz bardziej dom, metaforę drzewa lub oparte na zapytaniach podejście do uzyskiwania dostępu do technologii opartych na formacie XML, przydatnym sposobem koncepcyjnego koncepcyjnego przesyłania strumieniowego węzła XAML jest następujący sposób. Wyobraź sobie, że załadowany kod XAML jest modelem DOM lub drzewem, w którym każdy możliwy węzeł jest rozwijany w sposób liniowy, a następnie przedstawiany liniowo. W miarę przechodzenia przez węzły można przechodzić "w" lub "poza" poziomów, które byłyby istotne dla modelu DOM, ale strumień węzła XAML nie jest jawnie śledzone, ponieważ te pojęcia na poziomie nie są istotne dla strumienia węzła. Strumień węzła ma "bieżącą" pozycję, ale jeśli nie zapisano innych części strumienia samodzielnie jako odwołania, każdy aspekt strumienia węzła inny niż bieżące położenie węzła jest poza widokiem.

Koncepcja strumienia węzłów XAML ma godną uwagi zaletę, że jeśli przejdziesz przez cały strumień węzłów, masz pewność, że przetworzyno całą reprezentację XAML; Nie musisz martwić się, że zapytanie, operacja DOM lub inne nieliniowe podejście do przetwarzania informacji nie przegapiło części pełnej reprezentacji XAML. Z tego powodu reprezentacja strumienia węzła XAML jest idealna zarówno do łączenia czytników XAML i składników zapisywania XAML, jak i do udostępniania systemu, w którym można wstawić własny proces, który działa między fazami odczytu i zapisu operacji przetwarzania XAML. W wielu przypadkach kolejność węzłów w strumieniu węzłów XAML jest celowo zoptymalizowana lub zmieniana przez czytniki XAML w porównaniu z kolejnością wyświetlania kolejności w tekście źródłowym, binarnym lub grafie obiektów. To zachowanie ma na celu wymuszenie architektury przetwarzania XAML, w której składniki zapisywania XAML nigdy nie znajdują się w sytuacji, w której muszą wrócić do strumienia węzła. Najlepiej, aby wszystkie operacje zapisu XAML mogły działać na podstawie kontekstu schematu oraz bieżącej pozycji strumienia węzłów.

Podstawowa pętla węzła odczytu

Podstawowa pętla węzła odczytu do badania strumienia węzła XAML składa się z następujących pojęć. Na potrzeby pętli węzłów, jak opisano w tym temacie, załóżmy, że czytasz tekstowy plik XAML czytelny dla człowieka przy użyciu XamlXmlReader. Linki w tej sekcji odnoszą się do konkretnego interfejsu API pętli węzłów XAML zaimplementowanego przez XamlXmlReader.

  • Upewnij się, że nie jesteś na końcu strumienia węzła XAML (sprawdź IsEoflub użyj wartości zwracanej Read). Jeśli jesteś na końcu strumienia, nie ma bieżącego węzła i należy zamknąć.

  • Sprawdź, jakiego typu węzeł obecnie uwidacznia strumień węzła XAML, wywołując NodeType.

  • Jeśli masz skojarzony składnik zapisywania obiektów XAML połączony bezpośrednio, zazwyczaj wywołujesz WriteNode w tym momencie.

  • Na podstawie tego, XamlNodeType jest zgłaszany jako bieżący węzeł lub bieżący rekord, wywołaj jeden z następujących elementów, aby uzyskać informacje o zawartości węzła:

    • Aby uzyskać NodeTypeStartMember lub EndMember, zadzwoń Member, aby uzyskać XamlMember informacje o elemencie członkowskim. Element członkowski może być elementem XamlDirectivei dlatego nie musi być konwencjonalnym elementem członkowskim zdefiniowanym przez typ poprzedniego obiektu. Na przykład x:Name zastosowany do obiektu jest wyświetlany jako element członkowski XAML, w którym IsDirective jest prawdziwe, a Name elementu członkowskiego jest Name, a inne właściwości wskazują, że ta dyrektywa znajduje się w przestrzeni nazw XAML języka XAML.

    • Aby uzyskać NodeTypeStartObject lub EndObject, wywołaj Type, aby uzyskać XamlType informacje o obiekcie.

    • Aby uzyskać NodeTypeValue, wywołaj Value. Węzeł jest wartością tylko wtedy, gdy jest najprostszym wyrażeniem wartości elementu członkowskiego lub tekstem inicjowania obiektu (należy jednak pamiętać o zachowaniu konwersji typu, jak opisano w następnej sekcji tego tematu).

    • W przypadku NodeTypeNamespaceDeclarationwywołaj Namespace, aby uzyskać informacje o przestrzeni nazw dla węzła przestrzeni nazw.

  • Wywołaj Read, aby przejść czytnik XAML do następnego węzła w strumieniu węzła XAML i powtórzyć kroki ponownie.

Strumień węzła XAML udostępniany przez czytniki XAML usług .NET zawsze zapewnia pełny, głęboki przechodzenie wszystkich możliwych węzłów. Typowe techniki sterowania przepływem dla pętli węzłów XAML obejmują definiowanie treści w while (reader.Read())i włączanie NodeType w każdym punkcie węzła w pętli węzła.

Jeśli strumień węzła znajduje się na końcu pliku, bieżący węzeł ma wartość null.

Najprostsza pętla korzystająca z czytnika i składnika zapisywania przypomina poniższy przykład.

XamlXmlReader xxr = new XamlXmlReader(new StringReader(xamlStringToLoad));
//where xamlStringToLoad is a string of well formed XAML
XamlObjectWriter xow = new XamlObjectWriter(xxr.SchemaContext);
while (xxr.Read()) {
  xow.WriteNode(xxr);
}

Ten podstawowy przykład pętli węzła XAML ścieżki ładowania w sposób przezroczysty łączy czytnik XAML i składnik zapisywania XAML, co nie różni się od tego, czy użyto XamlServices.Parse. Jednak ta podstawowa struktura jest następnie rozszerzana w celu zastosowania do scenariusza odczytu lub zapisu. Niektóre możliwe scenariusze są następujące:

  • Włącz NodeType. Wykonywanie różnych akcji w zależności od typu węzła, który jest odczytywany.

  • Nie należy wywoływać WriteNode we wszystkich przypadkach. Wywołaj WriteNode tylko w niektórych przypadkach NodeType.

  • W ramach logiki dla określonego typu węzła przeanalizuj szczegóły tego węzła i wykonaj na nich działania. Można na przykład zapisywać tylko obiekty pochodzące z określonej przestrzeni nazw XAML, a następnie usuwać lub odroczyć wszystkie obiekty nie z tej przestrzeni nazw XAML. Możesz też usunąć lub w inny sposób ponownie przetworzyć wszelkie dyrektywy XAML, które system XAML nie obsługuje w ramach przetwarzania składowych.

  • Zdefiniuj niestandardowy XamlObjectWriter, który zastępuje metody Write*, prawdopodobnie wykonując mapowanie typów, które pomija kontekst schematu XAML.

  • Skonstruuj XamlXmlReader, aby używać kontekstu schematu XAML, tak aby dostosowane różnice w zachowaniu XAML były używane zarówno przez czytelnika, jak i moduł zapisywania.

Uzyskiwanie dostępu do kodu XAML poza koncepcją pętli węzła

Istnieją potencjalnie inne sposoby pracy z reprezentacją XAML inną niż pętla węzła XAML. Na przykład może istnieć czytnik XAML, który może odczytywać indeksowany węzeł lub w szczególności uzyskiwać dostęp do węzłów bezpośrednio przez x:Name, przez x:Uidlub za pośrednictwem innych identyfikatorów. Usługi XAML platformy .NET nie zapewniają pełnej implementacji, ale zapewniają sugerowany wzorzec za pośrednictwem usług i typów pomocy technicznej. Aby uzyskać więcej informacji, zobacz IXamlIndexingReader i XamlNodeList.

Praca z bieżącym węzłem

Większość scenariuszy korzystających z pętli węzła XAML nie tylko odczytuje węzły. Większość scenariuszy przetwarza bieżące węzły i przekazuje każdy węzeł pojedynczo do implementacji XamlWriter.

W typowym scenariuszu ścieżki obciążenia XamlXmlReader generuje strumień węzła XAML; węzły XAML są przetwarzane zgodnie z logiką i kontekstem schematu XAML; węzły są przekazywane do XamlObjectWriter. Następnie integrujesz wynikowy graf obiektu z aplikacją lub strukturą.

W typowym scenariuszu ścieżki zapisywania XamlObjectReader odczytuje graf obiektu, przetwarzane są poszczególne węzły XAML, a XamlXmlWriter wyprowadza zserializowany wynik jako plik tekstowy XAML. Kluczem jest to, że obie ścieżki i scenariusze obejmują pracę z dokładnie jednym węzłem XAML w danym momencie, a węzły XAML są dostępne do leczenia w ustandaryzowany sposób zdefiniowany przez system typów XAML i the.NET interfejsów API usług XAML.

Ramki i zakres

Pętla węzła XAML przechodzi przez strumień węzła XAML w sposób liniowy. Strumień węzła przechodzi do obiektów, do elementów członkowskich, które zawierają inne obiekty itd. Często warto śledzić zakres w strumieniu węzła XAML przez zaimplementowanie koncepcji ramki i stosu. Jest to szczególnie istotne w przypadku aktywnego dostosowywania strumienia węzła podczas jego pracy. Obsługa ramki i stosu zaimplementowana w ramach logiki pętli węzłów może zliczyć StartObject (lub GetObject) i EndObject zakresy podczas malenia do struktury węzła XAML, jeśli struktura jest uważana z perspektywy modelu DOM.

Przechodzenie i wprowadzanie węzłów obiektów

Pierwszy węzeł w strumieniu węzła, który jest otwierany przez czytnik XAML, jest węzłem start-object obiektu głównego. Z definicji ten obiekt jest zawsze pojedynczym węzłem obiektu i nie ma żadnych elementów równorzędnych. W każdym rzeczywistym przykładzie XAML obiekt główny jest zdefiniowany tak, aby miał co najmniej jedną właściwości, która zawiera więcej obiektów, a te właściwości mają węzły członkowskie. Węzły członkowskie mają następnie co najmniej jeden węzeł obiektu lub mogą również zakończyć działanie w węźle wartości. Obiekt główny zwykle definiuje zakresy nazw XAML, które są syntaktycznie przypisywane jako atrybuty w znaczniku tekstu XAML, ale mapują na typ węzła Namescope w reprezentacji strumienia węzła XAML.

Rozważmy następujący przykład XAML (jest to dowolny kod XAML, który nie jest wspierany przez istniejące typy na platformie .NET). Załóżmy, że w tym modelu obiektów FavorCollection jest List<T>Favor, Balloon i NoiseMaker można przypisać do Favor, właściwość Balloon.Color jest wspierana przez obiekt Color podobny do sposobu, w jaki WPF definiuje kolory jako znane nazwy kolorów, a Color obsługuje konwerter typów dla składni atrybutów.

Znaczniki XAML Wynikowy strumień węzła XAML
<Party węzeł Namespace dla Party
xmlns="PartyXamlNamespace"> węzeł StartObject dla Party
<Party.Favors> węzeł StartMember dla Party.Favors
węzeł StartObject dla niejawnych FavorCollection
StartMember węzeł dla niejawnej właściwości elementów FavorCollection.
<Balloon węzeł StartObject dla Balloon
Color="Red" węzeł StartMember dla Color

węzeł Value dla ciągu wartości atrybutu "Red"

EndMember dla Color
HasHelium="True" węzeł StartMember dla HasHelium

węzeł Value dla ciągu wartości atrybutu "True"

EndMember dla HasHelium
> EndObject dla Balloon
<NoiseMaker>Loudest</NoiseMaker> węzeł StartObject dla NoiseMaker

węzeł StartMember dla _Initialization

węzeł Value dla ciągu wartości inicjowania "Loudest"

węzeł EndMember dla _Initialization

EndObject dla NoiseMaker
EndMember węzeł dla niejawnej właściwości elementów FavorCollection.
węzeł EndObject dla niejawnych FavorCollection
</Party.Favors> EndMember dla Favors
</Party> EndObject dla Party

W strumieniu węzła XAML można polegać na następującym zachowaniu:

  • Jeśli istnieje węzeł Namespace, zostanie on dodany do strumienia bezpośrednio przed StartObject, który zadeklarował przestrzeń nazw XAML z xmlns. Ponownie przyjrzyj się poprzedniej tabeli ze strumieniem XAML i przykładowym węzłem. Zwróć uwagę, że węzły StartObject i Namespace wydają się być transponowane w porównaniu z ich położeniami deklaracji w znacznikach tekstowych. Jest to reprezentatywne zachowanie, w którym węzły przestrzeni nazw zawsze pojawiają się przed węzłem, do którego mają zastosowanie w strumieniu węzła. Celem tego projektu jest to, że informacje o przestrzeni nazw są istotne dla składników zapisywania obiektów i muszą być znane przed próbą wykonania mapowania typów przez składnik zapisywania obiektów lub przetworzenia obiektu w inny sposób. Umieszczenie informacji o przestrzeni nazw XAML przed zakresem aplikacji w strumieniu ułatwia zawsze przetwarzanie strumienia węzła w przedstawionej kolejności.

  • Z uwagi na powyższe zagadnienia jest to co najmniej jeden Namespace węzły, które są odczytywane jako pierwsze w większości rzeczywistych przypadków znaczników podczas przechodzenia węzłów od początku, a nie StartObject katalogu głównego.

  • Po węźle StartObject można wykonać StartMember, Valuelub bezpośrednio EndObject. Nigdy po nim nie następuje kolejny StartObject.

  • Po StartMember można wykonać StartObject, Valuelub bezpośrednio EndMember. Można go obserwować przez GetObject, dla elementów członkowskich, w których wartość ma pochodzić z istniejącej wartości obiektu nadrzędnego, a nie StartObject, która utworzy wystąpienie nowej wartości. Można go również wykonać za pomocą węzła Namespace, który ma zastosowanie do nadchodzącego StartObject. Nigdy po nim nie następuje kolejny StartMember.

  • Węzeł Value reprezentuje samą wartość; nie ma wartości "EndValue". Można go śledzić tylko EndMember.

    • Tekst inicjowania XAML obiektu, który może być używany przez konstrukcję, nie powoduje Object-Value struktury. Zamiast tego jest tworzony dedykowany węzeł członkowski o nazwie _Initialization. i ten węzeł członkowski zawiera ciąg wartości inicjowania. Jeśli istnieje, _Initialization jest zawsze pierwszym StartMember. _Initialization mogą być kwalifikowane w niektórych reprezentacjach usług XAML z zakresem nazw XAML języka XAML, aby wyjaśnić, że _Initialization nie jest zdefiniowaną właściwością w typach kopii zapasowych.

    • Kombinacja Member-Value reprezentuje ustawienie atrybutu wartości. W końcu może istnieć konwerter wartości zaangażowany w przetwarzanie tej wartości, a wartość jest zwykłym ciągiem. Nie jest to jednak oceniane, dopóki moduł zapisywania obiektów XAML nie przetworzy tego strumienia węzła. Składnik zapisywania obiektów XAML posiada niezbędny kontekst schematu XAML, mapowanie systemu typów i inną obsługę wymaganą do konwersji wartości.

  • Po węźle EndMember może znajdować się węzeł StartMember dla kolejnego elementu członkowskiego lub węzeł EndObject dla właściciela elementu członkowskiego.

  • Po węźle EndObject może znajdować się węzeł EndMember. Można go również obserwować za pomocą węzła StartObject w przypadkach, gdy obiekty są elementami równorzędnymi w elementach kolekcji. Można też skorzystać z węzła Namespace, który ma zastosowanie do nadchodzącego StartObject.

    • W przypadku unikatowego przypadku zamknięcia całego strumienia węzła EndObject katalogu głównego nie następuje nic; czytnik jest teraz na końcu pliku, a Read zwraca wartość false.

Konwertery wartości i strumień węzła XAML

Konwerter wartości jest ogólnym terminem dla rozszerzenia znaczników, konwertera typów (w tym serializacji wartości) lub innej dedykowanej klasy, która jest zgłaszana jako konwerter wartości za pośrednictwem systemu typów XAML. W strumieniu węzła XAML użycie konwertera typów i użycie rozszerzenia znaczników mają bardzo różne reprezentacje.

Konwertery typów w strumieniu węzła XAML

Zestaw atrybutów, który ostatecznie powoduje użycie konwertera typów, jest zgłaszany w strumieniu węzła XAML jako wartość elementu członkowskiego. Strumień węzła XAML nie próbuje utworzyć obiektu wystąpienia konwertera typów i przekazać do niego wartość. Użycie implementacji konwersji konwertera typów wymaga wywołania kontekstu schematu XAML i użycia go do mapowania typów. Nawet określenie, która klasa konwertera typów powinna być używana do przetwarzania wartości, wymaga pośrednio kontekstu schematu XAML. Jeśli używasz domyślnego kontekstu schematu XAML, te informacje są dostępne w systemie typów XAML. Jeśli potrzebujesz informacji o klasie konwertera typów na poziomie strumienia węzła XAML przed nawiązaniem połączenia z modułem zapisywania XAML, możesz uzyskać je z XamlMember informacji o ustawianym elemencie członkowskim. W przeciwnym razie dane wejściowe konwertera typów powinny być zachowywane w strumieniu węzła XAML jako zwykła wartość do czasu zakończenia pozostałych operacji, które wymagają systemu mapowania typów i kontekstu schematu XAML są wykonywane, na przykład tworzenie obiektu przez moduł zapisywania obiektów XAML.

Rozważmy na przykład następujący konspekt definicji klasy i użycie kodu XAML:

public class BoardSizeConverter : TypeConverter {
  //converts from string to an int[2] by splitting on an "x" char
}
public class GameBoard {
  [TypeConverter(typeof(BoardSizeConverter))]
  public int[] BoardSize; //2x2 array, initialization not shown
}
<GameBoard BoardSize="8x8"/>

Tekstowa reprezentacja strumienia węzła XAML dla tego użycia może być wyrażona jako następująca:

StartObject z XamlType reprezentującymi GameBoard

StartMember z XamlMember reprezentującymi BoardSize

węzeł Value z ciągiem tekstowym "8x8"

EndMember pasuje do BoardSize

EndObject pasuje do GameBoard

Zwróć uwagę, że w tym strumieniu węzła nie ma wystąpienia konwertera typów. Można jednak uzyskać informacje o konwerterze typów, wywołując XamlMember.TypeConverter w XamlMember dla BoardSize. Jeśli masz prawidłowy kontekst schematu XAML, możesz również wywołać metody konwertera, uzyskując wystąpienie z ConverterInstance.

Rozszerzenia znaczników w strumieniu węzła XAML

Użycie rozszerzenia znaczników jest zgłaszane w strumieniu węzła XAML jako węzeł obiektu w elemencie członkowskim, gdzie obiekt reprezentuje wystąpienie rozszerzenia znaczników. W związku z tym użycie rozszerzenia znaczników jest prezentowane bardziej jawnie w reprezentacji strumienia węzła niż użycie konwertera typów i zawiera więcej informacji. XamlMember informacji nie można było powiedzieć nic o rozszerzeniu znaczników, ponieważ użycie jest sytuacyjne i różni się w każdym możliwym przypadku narzutu; nie jest dedykowany i niejawny dla typu lub elementu członkowskiego, tak jak w przypadku konwerterów typów.

Strumień węzła reprezentacja rozszerzeń znaczników jako węzłów obiektów jest przypadek, nawet jeśli użycie rozszerzenia znaczników zostało wykonane w postaci atrybutu w adiustacji tekstu XAML (co jest często przypadkiem). Użycie rozszerzeń znaczników, które używały jawnego formularza elementu obiektu, są traktowane w ten sam sposób.

W węźle obiektu rozszerzenia znaczników mogą istnieć elementy członkowskie tego rozszerzenia znaczników. Reprezentacja strumienia węzła XAML zachowuje użycie tego rozszerzenia znaczników, niezależnie od tego, czy jest to użycie parametrów pozycyjnych, czy użycie z jawnie nazwanymi parametrami.

W przypadku użycia parametrów pozycyjnych strumień węzła XAML zawiera właściwość zdefiniowaną w języku XAML _PositionalParameters, która rejestruje użycie. Ta właściwość jest ogólnym List<T> z ograniczeniem Object. Ograniczenie to obiekt, a nie ciąg, ponieważ prawdopodobnie użycie parametrów pozycyjnych może zawierać użycie zagnieżdżonych rozszerzeń znaczników w nim. Aby uzyskać dostęp do parametrów pozycyjnych z użycia, możesz wykonać iterację po liście i użyć indeksatorów dla poszczególnych wartości listy.

W przypadku użycia nazwanego parametru każdy nazwany parametr jest reprezentowany jako węzeł członkowski tej nazwy w strumieniu węzła. Wartości składowe nie muszą być ciągami, ponieważ może istnieć użycie rozszerzenia znaczników zagnieżdżonych.

ProvideValue z rozszerzenia znaczników nie jest jeszcze wywoływana. Jest on jednak wywoływany w przypadku połączenia czytnika XAML i modułu zapisywania XAML w celu wywołania WriteEndObject w węźle rozszerzenia znaczników podczas badania go w strumieniu węzła. Z tego powodu zazwyczaj potrzebny jest ten sam kontekst schematu XAML, który będzie używany w celu utworzenia grafu obiektów na ścieżce ładowania. W przeciwnym razie ProvideValue z dowolnego rozszerzenia znaczników mogą zgłaszać wyjątki, ponieważ nie ma on oczekiwanych usług dostępnych.

Elementy członkowskie Language-Defined XAML i XML w strumieniu węzła XAML

Niektóre elementy członkowskie są wprowadzane do strumienia węzła XAML ze względu na interpretacje i konwencje czytnika XAML, a nie za pomocą jawnego wyszukiwania lub konstrukcji XamlMember. Często te elementy członkowskie są dyrektywami XAML. W niektórych przypadkach jest to czynność odczytywania kodu XAML, która wprowadza dyrektywę do strumienia węzła XAML. Innymi słowy, oryginalny tekst wejściowy XAML nie określił jawnie dyrektywy składowej, ale czytnik XAML wstawia dyrektywę w celu spełnienia strukturalnej konwencji XAML i informacji o raporcie w strumieniu węzła XAML przed utratą tych informacji.

Poniższa lista zawiera informacje o wszystkich przypadkach, w których oczekuje się, że czytnik XAML wprowadzi węzeł członkowski dyrektywy XAML oraz sposób identyfikowania tego węzła członkowskiego we wdrożeniach usług XAML platformy .NET.

  • tekst inicjowania węzła obiektu: Nazwa tego węzła członkowskiego jest _Initialization, reprezentuje dyrektywę XAML i jest zdefiniowana w przestrzeni nazw XAML języka XAML. Możesz pobrać dla niej jednostkę statyczną z Initialization.

  • parametry pozycyjne rozszerzenia znaczników: Nazwa tego węzła członkowskiego jest _PositionalParametersi jest zdefiniowana w przestrzeni nazw XAML języka XAML. Zawsze zawiera ogólną listę obiektów, z których każdy jest wstępnie oddzielony parametrem pozycyjnym przez podzielenie na znak ogranicznika , podany w wejściowym języku XAML. Możesz uzyskać jednostkę statyczną dla dyrektywy parametrów pozycyjnych z PositionalParameters.

  • Nieznana zawartość: Nazwa tego węzła członkowskiego to _UnknownContent. Ściśle rzecz biorąc, jest to XamlDirectivei jest zdefiniowany w przestrzeni nazw XAML języka XAML. Ta dyrektywa jest używana jako sentinel w przypadkach, gdy element obiektu XAML zawiera zawartość w źródłowym języku XAML, ale nie można określić właściwości zawartości w kontekście schematu XAML aktualnie dostępnego. Ten przypadek można wykryć w strumieniu węzła XAML, sprawdzając elementy członkowskie o nazwie _UnknownContent. Jeśli w strumieniu węzła XAML ścieżki obciążenia nie zostanie podjęta żadna inna akcja, domyślna XamlObjectWriter zgłasza próbę WriteEndObject, gdy napotka element członkowski _UnknownContent na dowolnym obiekcie. Domyślny XamlXmlWriter nie zgłasza i traktuje element członkowski jako niejawny. Możesz uzyskać jednostkę statyczną dla _UnknownContent z UnknownContent.

  • Właściwość Collection kolekcji: Chociaż typ kopii zapasowej CLR klasy kolekcji używanej dla języka XAML ma zazwyczaj dedykowaną właściwość o nazwie, która zawiera elementy kolekcji, ta właściwość nie jest znana systemowi typów XAML przed rozpoznawaniem typu kopii zapasowej. Zamiast tego strumień węzła XAML wprowadza symbol zastępczy Items jako element członkowski typu XAML kolekcji. W implementacji usług XAML platformy .NET nazwa tej dyrektywy lub elementu członkowskiego w strumieniu węzła to _Items. Stała dla tej dyrektywy można uzyskać z Items.

    Należy pamiętać, że strumień węzła XAML może zawierać właściwość Items z elementami, które nie mogą być analizowalne na podstawie rozdzielczości typu kopii zapasowej i kontekstu schematu XAML. Na przykład

  • składowych zdefiniowanych w formacie XML: zdefiniowane xml:baseXML, xml:lang i xml:space składowe są zgłaszane jako dyrektywy XAML o nazwie base, langi space w implementacjach usług XAML platformy .NET. Przestrzeń nazw dla nich to przestrzeń nazw XML http://www.w3.org/XML/1998/namespace. Stałe dla każdego z nich można uzyskać z XamlLanguage.

Kolejność węzłów

W niektórych przypadkach XamlXmlReader zmienia kolejność węzłów XAML w strumieniu węzła XAML, a kolejność, w przypadku wyświetlania węzłów w adiustacji lub przetwarzania jako XML. Jest to wykonywane w celu uporządkowania węzłów tak, aby XamlObjectWriter mógł przetwarzać strumień węzła w sposób tylko do przodu. W usługach XAML platformy .NET czytnik XAML zmienia kolejność węzłów, a nie pozostawia tego zadania składnikowi zapisywania XAML jako optymalizacji wydajności składników zapisywania obiektów XAML odbiorców strumienia węzła.

Niektóre dyrektywy mają na celu dostarczenie dodatkowych informacji na temat tworzenia obiektu z elementu obiektu. Te dyrektywy to: Initialization, PositionalParameters, TypeArguments, FactoryMethod, Arguments. Czytniki XAML usług .NET XAML próbują umieścić te dyrektywy jako pierwsze elementy członkowskie w strumieniu węzła po StartObjectobiektu z powodów, które zostały wyjaśnione w następnej sekcji.

Zachowanie elementu XamlObjectWriter i kolejność węzłów

StartObject do XamlObjectWriter niekoniecznie jest sygnałem modułu zapisywania obiektów XAML w celu natychmiastowego konstruowania wystąpienia obiektu. Język XAML zawiera kilka funkcji językowych, które umożliwiają zainicjowanie obiektu z dodatkowymi danymi wejściowymi, a nie poleganie całkowicie na wywoływaniu konstruktora bez parametrów w celu utworzenia obiektu początkowego, a dopiero następnie ustawiania właściwości. Te funkcje obejmują: XamlDeferLoadAttribute; tekst inicjowania; x:TypeArguments; parametry pozycyjne rozszerzenia znaczników; metody fabryki i skojarzone x:Argumenty węzłów (XAML 2009). Każdy z tych przypadków opóźnia rzeczywistą konstrukcję obiektu, a ponieważ strumień węzła jest zmieniany, moduł zapisywania obiektów XAML może polegać na zachowaniu rzeczywistego konstruowania wystąpienia za każdym razem, gdy napotkano element członkowski rozpoczęcia, który nie jest specjalnie dyrektywą budowlaną dla tego typu obiektu.

GetObject

GetObject reprezentuje węzeł XAML, w którym zamiast konstruować nowy obiekt, moduł zapisywania obiektów XAML powinien zamiast tego uzyskać wartość właściwości zawierającej obiekt. Typowy przypadek, w którym węzeł GetObject występuje w strumieniu węzła XAML, dotyczy obiektu kolekcji lub obiektu słownika, gdy właściwość zawierająca jest celowo tylko do odczytu w modelu obiektów typu zapasowego. W tym scenariuszu kolekcja lub słownik często jest tworzona i inicjowana (zwykle pusta) przez logikę inicjowania typu własnego.

Zobacz też