Wzorzec architektoniczny Model View ViewModel (2/2) « Pabloware + Windows Phone

Pabloware + Windows Phone

Niezależny blog firmy Pabloware o systemie Windows® Phone 7

Wzorzec architektoniczny Model View ViewModel (2/2)

Warstwa View

Ostatnia do omówienia we wzorcu architektonicznym MVVM jest warstwa View. Jest to warstwa odpowiedzialna za wygląd interfejsu użytkownika aplikacji. Jako pojedynczy element warstwy View (czyli jeden widok), w przypadku aplikacji dla Windows Phone 7 rozumie się stronę aplikacji, choć jest to granica umowna, bo można też pod tą nazwą rozumieć rozbudowaną kontrolkę niestandardową, okno wyskakujące, itp.

W technologiach Silverlight i WPF warstwa View składa się z dwóch części. Podstawową częścią jest plik XAML, zawierający deklaratywny opis interfejsu użytkownika. Opcjonalną częścią jest plik code-behind, w którym może zostać umieszczony kod programu, związany z tym interfejsem użytkownika.

Część warstwy View, zawarta w pliku XAML, jest zawsze niezależna od warstwy ViewModel. Wskazuje się w niej wprawdzie konkretne miejsca warstwy ViewModel, ale nie jest ona kompilowana, nie może więc być z naszego punktu widzenia zależna. Co więcej, można przygotować dla niej testowe dane statyczne, używane podczas graficznego projektowania widoku.

Sprawia to, że możliwe jest całkowite oddzielnie roli projektanta interfejsu użytkownika od roli programisty, bo projektant nie musi mieć dostępu do stworzonego przez programistę kodu źródłowego programu, żeby stworzyć widok interfejsu użytkownika, od razu wiążąc go z przygotowaną wcześniej przez programistę warstwą ViewModel. Jest to często podawana zaleta wzorca architektonicznego MVVM i formatu XAML, choć oczywiście jest prawdziwie przydatna jedynie w odpowiednio dużych i złożonych pod względem graficznym projektach. W małych lub prostych graficznie projektach, w których programista często nie korzysta nawet z graficznego trybu projektowania, ręcznie pisząc kod XAML, jest ona, zdaniem autora, pomijalna.

Aby uzyskać wiązania danych z kontrolką interfejsu użytkownika, deklaruje się je w pliku XAML, przy czym dane te pochodzą z warstwy ViewModel, nazywanej źródłem wiązania i są wiązane z tzw. celem wiązania. Pod względem implementacji, warstwa ViewModel, jedynie musi udostępnić te dane w taki sposób, aby warstwa View była informowana o ich zmianie, co czyni się implementując bardzo prosty interfejs INotifyPropertyChanged. Z kolei kontrolki interfejsu użytkownika muszą dziedziczyć po klasie DependencyObject i używać klasy DependencyProperty, aby ich właściwości mogły być wiązane.

Oprócz wiązania danych, w pliku XAML możliwe jest również „wiązanie” zachowań aplikacji (np. reakcji na naciśnięcie przycisku), poprzez wykorzystanie mechanizmu komend (ang. command). Jednak jedyną korzyścią z takiej strategii jest możliwość „wiązania”, przez projektanta interfejsu użytkownika (a nie tylko przez programistę), zachowań aplikacji z poszczególnymi elementami interakcji z interfejsem użytkownika. Poważną wadą mechanizmu komend jest ilość kodu, jaka musi zostać, na etapie programowania, dodana do projektu, aby udostępnić pojedynczą komendę, co powoduje niepotrzebne komplikowanie projektu. Użycie komend powoduje także niepotrzebne spowolnienie aplikacji pod systemem Windows Phone 7.

W związku z powyższym, autor rezygnuje na ten moment z użycia komend, gdy nie niosą one żadnych korzyści, a mają poważne wady. Jedynym sposobem wiązania interfejsu użytkownika z zachowaniami udostępnianymi przez warstwę ViewModel, pozostaje wtedy plik code-behind.

Plik ten, jak już wcześniej napisano, jest opcjonalny i w „ekstremalnej” wersji wzorca architektonicznego MVVM jest prawie lub całkowicie pusty. Jednak umieszczenie w tym pliku bezargumentowych, pojedynczych wywołań, odpowiednio przygotowanych metod klas warstwy ViewModel, w metodach obsługi zdarzeń interfejsu użytkownika, nie wprowadza żadnej dodatkowej komplikacji. Jest dokładnie tym samym, pod względem np. możliwości testowania kodu, co „wiązanie” komend, ale pozbawionym wymienionych wad komend.

Innym przykładem kodu, który według wielu osób można umieszczać w pliku code-behind, jest kod operujący tylko i wyłącznie na interfejsie użytkownika, bez bezpośredniego związku z logiką aplikacji. Do tej kategorii należą np.: pokazywanie okien dialogowych, uruchamianie dekoracyjnych animacji lub ustawianie ogniska na kontrolce.

Można wyobrazić sobie nawet rezygnację z mechanizmu automatycznych wiązań danych i w konsekwencji ręczne przepisywanie, w pliku code-behind, danych z obiektu ViewModel do kontrolek interfejsu użytkownika. W środowisku Windows Phone 7 niosłoby to za sobą pewną korzyść wydajnościową, ale powodowałoby rozbudowanie i utrudnienie w zarządzaniu plikiem code-behind. Wprawdzie pod względem testowania kodu nie różniłoby się niczym od stosowania wiązań danych w pliku XAML, ale tylko przy założeniu, że dane te byłyby statyczne. Obsługiwanie zmiany danych wprowadza bowiem trudną do zaakceptowania, w nietestowanej warstwie View, komplikację kodu.

Podsumowanie

Wzorzec architektoniczny MVVM niesie za sobą możliwość podziału aplikacji na luźno ze sobą połączone warstwy. Powoduje to, że aplikacje stają się bardziej rozszerzalne i łatwiejsze w zarządzaniu. Umożliwia także pełniejsze ich testowanie. Sprzyja ich modularyzacji, mającej na celu lepszy podział pracy nad aplikacją.

Elastyczność tego wzorca projektowego zachęca do stosowania go w wyważony sposób, w zgodzie z możliwościami środowiska, takiego jak np. telefon komórkowy. Chociaż dostępnych jest wiele, bardzo się od siebie różniących, gotowych bibliotek ułatwiających implementację tego wzorca, dostarczających do tego celu gotowego szkieletu, autor na ten moment nie decyduje się na skorzystanie z żadnej z tych bibliotek, ponieważ w ten sposób można wybrać z tego wzorca najlepsze elementy, nie obciążając budowanych aplikacji dodatkową biblioteką.

Za zastosowaniem tego wzorca architektonicznego w aplikacjach, przemawia głównie możliwość wykonywania testów jednostkowych na praktycznie całym kodzie aplikacji. Albowiem można w ten sposób podnieść niezawodność aplikacji. Również istotna jest duża rozszerzalność stosującego ten wzorzec kodu, gdyż umożliwia to jego łatwe rozbudowywanie. Ponadto trzeba podkreślić, że wzorzec ten może sprzyjać stosowaniu dobrych zasad projektowych, choć niesie w tym zakresie też zagrożenia.

Ponadto można spotkać się z opiniami, że zrozumienie podstawowych zasad wzorca MVVM, nawet gdy nie zamierzamy stosować go w praktyce, pozwala lepiej zrozumieć filozofię bibliotek WPF i Silverlight. Zrozumienie biblioteki Silverlight jest niezbędne do tworzenia aplikacji użytkowych, przeznaczonych dla systemu Windows Phone 7.

No Responses to “Wzorzec architektoniczny Model View ViewModel (2/2)”

Kanał RSS z komentarzami do tego wpisu. TrackBack URL

Leave a Response