MVVM - správné praktiky a dynamické vytvoření vizuálního objektu

Hanz

Dobrý den,

chtěl bych Vás požádat o názor.

Jedná se podle vás o dobrou praktiku vytvořit ve ViewModelu nějaký vizuální objekt/y a pak ho umístit do View? Vím jak. Nicméně našel jsem převážně na stackoverflow nějaké věci k tomuto tématu, ale v podstatě žádnou shodu názorů v diskuzi.

S pozdravem


Tomáš Roll

Je to velmi špatná praktika. Použij delegáta nebo rozhraní, kterým dáš z ViewModelu do View najevo, že chceš něco vytvořit. ViewModel by neměl nic vědět o View a jeho komponentách. Nějaký WPF guru by ti určitě z hlavy napsal template, se kterou bys to udělal zcela čistě přímo ve ViewModelu, ale k takovým já nepatřím a každá technologie je dobrý sluha, ale zlý pán, někdy je lepší 5 řádku kódu než 50 řádku template.

Hanz

A opačně prosím , pokud budu mít ve view v nějakém kontejneru (např. Canvas.Children ) nějaké vizuální objekty stejného typu a chtěl bych některé jejich vlastnosti (left, right, visible, zpětné volání PropertyChanged...) předat do viewModelu (nechci tam předat kolekci závislou na konkrétním ui frameworku, zde wpf), znám DataContext z view - tedy volání je uskutečnitelné.

Toto je už samozřejmě konkrétní dotaz. Toto by bylo čisté, prosím?

Děkuji

Tomáš Roll

Jistě, ve ViewModel bys měl mít kolekci objektů, které by byly nevizuálními protějšky těch vizuálních z View a tam bys ukládal věci jako souřadnice, velikost nebo barvu. Já mám takhle vyřešený ERD Designer, ale nemám to přibindované, protože při pár tisících entit by to asi výkonově chcíplo, (dobrý nápad na otestování, asi to zkusím) řeším to čistě programově. Ale pořád ViewModel neví nic o View. Díky tomu jsem mohl udělat dvě verze View, jedna jede přes WPF komponenty, druhá přímo vykresluje. Ta druhá je 2x rychlejší, ale taky pracnější.

Adusko

A opačně prosím , pokud budu mít ve view v nějakém kontejneru (např. Canvas.Children ) nějaké vizuální objekty stejného typu a chtěl bych některé jejich vlastnosti (left, right, visible, zpětné volání PropertyChanged...) předat do viewModelu (nechci tam předat kolekci závislou na konkrétním ui frameworku, zde wpf), znám DataContext z view - tedy volání je uskutečnitelné.

Toto je už samozřejmě konkrétní dotaz. Toto by bylo čisté, prosím?

Děkuji

Spárovanie medzi ModelView a View je možné urobiť cez DataTemplate pričom vo View si vlastnosti nabinduješ.

Kód: [Vybrat]
    <DataTemplate DataType="{x:Type vm:TestPartViewModel}">
        <v:TestPartView />
    </DataTemplate>

Nemám skúsenosť s bindovaním ItemsSource na Canvas ale podľa tohto linku by sa to malo dať urobiť.

http://stackoverflow.com/questions/7177432/how-to-display-items-in-canvas-through-binding

V prípade že máš veľa položiek z ktorých sa zobrazuje iba časť, tak by si si mohol urobiť virtualizáciu aby sa do Canvasu nenačítavali všetky, ale iba tie čo sú vo výreze. Prípadne mať viac verzíí View od jednoduchej až po zložitú a podľa počtu položiek vybrať tú správnu  :)

Čo sa týka virtualizácie, tak som myslel niečo takéto: http://www.zagstudio.com/blog/497