c# - listbox with 2 different Datatemplates -
need view 2 different controls need add listbox. controls of type icontrol
so did following:
controls.cs
interface icontrol { double x { get; set; } double y { get; set; } } class mybutton : button, icontrol, inotifypropertychanged { public mybutton(string buttontext, double x, double y) { this.content = buttontext; this.x = x; this.y = y; } private double x = 0; private double y = 0; public mybutton() { } public double x { { return x;} set { x = value; onpropertychanged("x"); } } public double y { { return y;} set { y = value; onpropertychanged("y"); } } } class mylabel : label, icontrol, inotifypropertychanged { public mylabel(int number, double x, double y) { this.content = number.tostring(cultureinfo.invariantculture); this.x = x; this.y = y; } private double x = 0; private double y = 0; public mylabel() { } public double x { get{ return x;} set { x = value; onpropertychanged("x"); } } public double y { get{ return y;} set { y = value; onpropertychanged("y"); } } }
now in viewmodel.cs have
class viewmodel { private readonly observablecollection<icontrol> controls = new observablecollection<icontrol>(); public viewmodel() { var m1 = new mybutton("test string inside button",0,0); var m2 = new mylabel(1123, 0, 80); controls.add(m1); controls.add(m2); } public observablecollection<icontrol> controls { {return controls;} } }
and in mainwindow.xaml
<listbox x:name="listbox" itemssource="{binding controls}" selectionmode="extended" > <listbox.resources> <datatemplate x:key="buttontemplate" datatype="{x:type local:mybutton}"> <button content="{binding}" mousedown="button_mousedown" previewmouseup="button_mouseup" previewmousemove="button_mousemove" /> </datatemplate> <datatemplate x:key="labeltemplate" datatype="{x:type local:mylabel}"> <label content="{binding}" background="aqua"/> </datatemplate> </listbox.resources> <listbox.itemspanel> <itemspaneltemplate> <canvas/> </itemspaneltemplate> </listbox.itemspanel> <listbox.itemcontainerstyle> <style targettype="listboxitem" > <setter property="canvas.left" value="{binding x}" /> <setter property="canvas.top" value="{binding y}" /> </style> </listbox.itemcontainerstyle> </listbox>
the listbox showing mybutton , mylabel added observablecollection, datatemplates doing nothing. events in buttontemplate not firing, , background of label not set.
what wrong ? appreciated.
thanks in advance
the first problem.
bad idea, in general, inherit view model layer types visual
, descendants (like control
). define view models in view model layer:
// former icontrol, renamed avoid confusing view layer public interface icanvasitem { object content { get; set; } double x { get; set; } double y { get; set; } } public class mybutton : icanvasitem, inotifypropertychanged { /* ... */} public class mylabel : icanvasitem, inotifypropertychanged { /* ... */}
the second problem. template lookup items control can performed in 3 ways:
- using
itemtemplate
property. not option, since need 2 different templates; - using
datatemplateselector
viaitemtemplateselector
property; - using default templates per type, declared somewhere in resource dictionaries.
you're going third way, but, templates has key, , doesn't allow templates applied default. fix this, throw away x:key
attributes, , let type template key:
<listbox.resources> <datatemplate datatype="{x:type local:mybutton}"> <button content="{binding content}" mousedown="button_mousedown" previewmouseup="button_mouseup" previewmousemove="button_mousemove" /> </datatemplate> <datatemplate datatype="{x:type local:mylabel}"> <label content="{binding content}" background="aqua"/> </datatemplate> </listbox.resources>
more data templating read here: http://msdn.microsoft.com/en-us/library/ms742521%28v=vs.110%29.aspx
Comments
Post a Comment