MVVM w JavaScript, knockout.js

Od jakiegoś czasu, coraz więcej czasu poświęcam nad aplikacjami webowymi stąd na blogu tematyka trochę zmieniła się z kodu czysto server-side na web. Większość programistów C# nie przepada za JavaScript, ale trzeba robić wszystko, aby ułatwić sobie codzienną pracę. Istnieje wiele dodatkowych bibliotek do JS i to dzięki nim środowisko JS jest tak potężne. Na blogu raczej nie będę zajmował się zbytnio tą tematyką ponieważ nie jest to do końca moja specjalizacja. Czasami jednak, tak jak dzisiaj, wrzucę kilka słów o ciekawych według mnie bibliotekach, które powinny znaleźć się w każdym webowym projekcie. Jako, że sporo korzystałem z WPF, to wzorzec MVVM był dla mnie codziennością. Z tego względu, biblioteka knockout od razu zaciekawiła mnie.

O czystym MVVM pisałem już np. tutaj:

http://www.pzielinski.com/?p=1055

Zdefiniujemy najpierw nasz widok. W przypadku WPF, robiło to się za pomocą XAML oraz dyrektyw {Binding}. Zobaczmy jak to wygląda w HTML i knockout.js:

<p data-bind="text: firstName"></p>
<p data-bind="text: lastName"></p>

Nie wygląda to aż tak brzydko… Korzystamy z atrybutu data-bind a następnie określamy za pomocą text, że chcemy powiązać tekst, który znajduje się w danej właściwości. Oczywiście musimy stworzyć również ViewModel:

var personViewModel =  { firstName: 'Piotr', lastName:'Zielinski' };
ko.applyBindings(personViewModel);

Aby wykonać wiązanie należy wywołać metodę applyBindings na obiekcie ko (knockout.js). Jak widać, nie jest to trudne i dzięki temu oddzielimy logikę od warstwy prezentacji. Korzystając z czystego JS, można napisać naprawdę brzydki kod i projekt. Na szczęście mnogość bibliotek (np. RequireJS) pozwalają na zastosowanie tego języka w bardziej skomplikowanych projektach.

Spróbujmy napisać trochę inny przykład, pokazujący wiązanie w drugą stronę. Innymi słowy, chcemy aby użytkownik mógł modyfikować dane. Typowy scenariusz to oczywiście zwykły formularz. Musimy zmodyfikować nieco nasz ViewModel. W C# zwykle wystarczy dodać SETTER do danej właściwości.

var personViewModel = { 
firstName: ko.observable('poczatkowa wartosc'), 
lastName: ko.observable('poczatkowa wartosc') };

ko.applyBindings(personViewModel);

Musimy skorzystać z metody observable. W WPF zwykle korzysta się z INotifyPropertyChanged oraz OnPropertyChanged. Pełni to analogiczną funkcję – pozwala wykryć, kiedy właściwość została zmieniona. Następnie musimy dodać dwa nowe pola edycyjne:

<p data-bind="text: firstName"></p>
<p data-bind="text: lastName"></p>

<input type="text" data-bind='value: firstName'/>
<input type="text" data-bind='value: lastName'/>

To co rzuca tutaj się w oczy, to nowy typ wiązania, a mianowicie “value”. Korzystamy z niego, gdy daną wartością chcemy zaktualizować właściwość. W WPF, korzysta się z typu wiązana (OneWay, TwoWay itp.), aby osiągnąć analogiczny efekt.

Uruchamiając przykład, zobaczymy, że zmieniając dane w polu edycyjnym, zostaną one również odzwierciedlone w tag’u <p>.

Na dzisiaj wystarczy. W przyszłych wpisach pokażę trochę więcej przykładów. Osobiście uważam, że biblioteka jest bardzo przydatna i naturalna dla programistów, którzy pracują również sporo z WPF.

Leave a Reply

Your email address will not be published.