<dxg:LookUpEdit Margin="5" HorizontalAlignment="Stretch" VerticalAlignment="Center"
ItemsSource="{Binding}"
DisplayMember="Name"
AutoPopulateColumns="False">
<dxg:LookUpEdit.PopupContentTemplate>
<ControlTemplate>
<dxg:GridControl Name="PART_GridControl">
<dxg:GridControl.Columns>
<dxg:GridColumn FieldName="Name"/>
<dxg:GridColumn FieldName="Date"/>
</dxg:GridControl.Columns>
</dxg:GridControl>
</ControlTemplate>
</dxg:LookUpEdit.PopupContentTemplate>
</dxg:LookUpEdit>
please help me, I do not know how to add GridColumn on GridControl and set LookUpEdit.PopupContentTemplate = GridControl
Thank you very much. I think XAMLREADER can help me, I'm stuck here
ControlTemplate ct = new ControlTemplate();
FrameworkElementFactory gridcontrol = new FrameworkElementFactory(typeof(GridControl));
FrameworkElementFactory gridcolumn = new FrameworkElementFactory(typeof(GridColumn));
gridcontrol.SetValue(?, ?);
gridcolumn.SetValue(?, ?);
ct.VisualTree = gridcontrol;
creating control/data templates in code behind involves factory classes, that may be more complicated for non framework types.
example from Creating a control template with code behind
ControlTemplate template = new ControlTemplate(typeof(ListBoxItem));
FrameworkElementFactory elemFactory = new FrameworkElementFactory(typeof(Border));
elemFactory.Name = "Border";
elemFactory.SetValue(Border.CornerRadiusProperty, new CornerRadius(5));
elemFactory.SetValue(Border.PaddingProperty, new Thickness(1));
elemFactory.SetValue(Border.SnapsToDevicePixelsProperty, true);
template.VisualTree = elemFactory;
//same can be used as
LookUpEdit.PopupContentTemplate = template;
above is just an example, you may need to use the appropriate types
alternatively keeping the control templates in resource dictionary may help you
or the easiest solution is to parse the xaml in code behind
const string xaml = "<ControlTemplate><dxg:GridControl Name=""PART_GridControl""><dxg:GridControl.Columns><dxg:GridColumn FieldName=""Name""/><dxg:GridColumn FieldName=""Date""/></dxg:GridControl.Columns></dxg:GridControl></ControlTemplate>";
ControlTemplate template = XamlReader.Parse(xaml) as ControlTemplate;
//this can be used as
LookUpEdit.PopupContentTemplate = template;
Related
I started by making a label in XAML with its content bound to a string in my resources file. I've implemented localization and confirm that when I change languages, the label's content updates accordingly.
Now I need to do the same from code behind.
Here is a taste of the XAML:
<Grid Background="#FF313131">
<ScrollViewer>
<StackPanel x:Name="GeneralTab_StackPanel">
<WrapPanel VerticalAlignment="Top" Background="{Binding AxisDataColorCode}" Margin="2,2,2,0">
<Label x:Name="lbl_General_MachineType" Content="{Binding GUI_MachineType, Source={StaticResource Resources}}" FontSize="20" />
<Label x:Name="lbl_General_MachineTypeResult" Content="{Binding MachineBaseType}" FontSize="20" />
</WrapPanel>
<WrapPanel....
Attempting to recreate this in code-behind I have the following:
Binding BgColorBinding = new Binding("AxisDataColorCode");
// Something needs to change here. I've tried a bunch of things already with no luck.
Binding GUI_MachineTypeBinding = new Binding("GUI_MachineType");
GUI_MachineTypeBinding.Source = Properties.Resources.GUI_MachineType;
Binding MachineBaseTypeBinding = new Binding("MachineBaseType");
Label Label_MachineType = new Label();
Label_MachineType.Name = "lbl_General_MachineType";
Label_MachineType.FontSize = 20;
// This does not work at all. Help!
Label_MachineType.SetBinding(Label.ContentProperty, GUI_MachineTypeBinding);
// this works! but it's not a binding and doesn't update...
// Label_MachineType.Content = Properties.Resources.GUI_MachineType;
Label Label_MachineTypeResult = new Label();
Label_MachineTypeResult.Name = "lbl_General_MachineTypeResult";
Label_MachineTypeResult.FontSize = 20;
Label_MachineTypeResult.SetBinding(Label.ContentProperty, MachineBaseTypeBinding);
WrapPanel MachineTypeWrapPanel = new WrapPanel();
MachineTypeWrapPanel.Name = "MachineTypeWrapPanel";
MachineTypeWrapPanel.VerticalAlignment = System.Windows.VerticalAlignment.Top;
MachineTypeWrapPanel.Margin = new Thickness(2, 2, 2, 0);
MachineTypeWrapPanel.SetBinding(WrapPanel.BackgroundProperty, BgColorBinding);
MachineTypeWrapPanel.Children.Add(Label_MachineType);
MachineTypeWrapPanel.Children.Add(Label_MachineTypeResult);
My other bindings work fine, because I've just tied them to properties in code behind that implement property changed notification.
Trying to bind to any of the keys in my resources however, gives me nothing. The label's content is simply blank, and there are no errors in my debug output window.
I can't find any examples of anyone binding to their Properties.Resources.Whatever from code behind anywhere.
The solution:
Thanks Henka!
Binding GUI_MachineTypeBinding = new Binding("GUI_MachineType");
GUI_MachineTypeBinding.Source = Application.Current.FindResource("Resources");
....
Label_MachineType.SetBinding(Label.ContentProperty, GUI_MachineTypeBinding);
If you set the Binding from code behind the UI will not be notified you should create your custom extension and save a WeakReference to the DependencyProperty and update the value when the culture changed, i propose an other solution to use, have a look at this article.Advanced WPF Localization
I want to add a button on every row of WPF grid which I am binding from code behind. I am very new to WPF any help is appreciated.
My current code for binding grid is:
DataGridTextColumn c1 = new DataGridTextColumn();
c1.Header = "Dummy column";
c1.Binding = new Binding("DummyColumn");
c1.IsReadOnly = true;
grdDummy.Columns.Add(c1);
foreach (DummyObject deal in AllDummyObjects)
{
ModelToBind dataModel = new ModelToBind()
//do some processing on dataModel
grdDummy.Items.Add(dataModel);
}
You can add another column with button like this:
DataGridTemplateColumn buttonColumn = new DataGridTemplateColumn();
DataTemplate buttonTemplate = new DataTemplate();
FrameworkElementFactory buttonFactory = new FrameworkElementFactory(typeof (Button));
buttonTemplate.VisualTree = buttonFactory;
//add handler or you can add binding to command if you want to handle click
buttonFactory.AddHandler(ButtonBase.ClickEvent, new RoutedEventHandler(HandleClick));
buttonFactory.SetValue(ContentProperty, "Button");
buttonColumn.CellTemplate = buttonTemplate;
grdDummy.Columns.Add(buttonColumn);
Previously, an example was given of creating a Button using FrameworkElementFactory.
This class is not recommended.
Quote from the documentation:
This class is a deprecated way to programmatically create templates, which are subclasses of FrameworkTemplate such as ControlTemplate or DataTemplate; not all of the template functionality is available when you create a template using this class. The recommended way to programmatically create a template is to load XAML from a string or a memory stream using the Load method of the XamlReader class.
In this regard, I show the implementation code using the XamlReader.
The code is shown from the assumption that the ModelToBind class has a command-property named ButtonCommand and property ButtonTitle.
And this class is located in the local namespace "Febr20y" in the assembly of the same name.
DataGridTextColumn c1 = new DataGridTextColumn
{
Header = "Dummy column",
Binding = new Binding("DummyColumn"),
IsReadOnly = true
};
DataTemplate template = (DataTemplate)XamlReader.Parse(
#"<DataTemplate
xmlns='http://schemas.microsoft.com/winfx/2006/xaml/presentation'
xmlns:x='http://schemas.microsoft.com/winfx/2006/xaml'
xmlns:local='clr-namespace:Febr20y;assembly=Febr20y'
DataType ='{x:Type local:ModelToBind}'>
<Button Content='{Binding ButtonTitle, Mode=OneWay}'
Command='{Binding ButtonCommand, Mode=OneWay}'/>
</DataTemplate>");
DataGridTemplateColumn c2 = new DataGridTemplateColumn()
{
Header = "Buttons",
IsReadOnly = true,
CellTemplate=template
};
grdDummy.Columns.Add(c1);
grdDummy.Columns.Add(c2);
var listSource = AllDummyObjects
.Select(deal => new ModelToBind() { ButtonTitle = deal.Title.ToString()})
.ToList();
grdDummy.ItemsSource = listSource;
This is equivalent to this XAML code:
<DataGrid x:Name="grdDummy" AutoGenerateColumns="False">
<DataGrid.Columns>
<DataGridTextColumn Binding="{Binding DummyColumn}"
IsReadOnly="True"
Header="Dummy column"/>
<DataGridTemplateColumn Header="Buttons"
IsReadOnly="True">
<DataGridTemplateColumn.CellTemplate>
<DataTemplate DataType="{x:Type local:ModelToBind}">
<Button Content="{Binding ButtonTitle, Mode=OneWay}"
Command="{Binding ButtonCommand, Mode=OneWay}"/>
</DataTemplate>
</DataGridTemplateColumn.CellTemplate>
</DataGridTemplateColumn>
</DataGrid.Columns>
</DataGrid>
I am currently try to programatically get the ListBox
I tried to find many ways but, I can't make this works.
Here is the xaml part of code:
<ListBox Grid.Row="2" Grid.ColumnSpan="2" x:Name="PeerList" Margin="10,10,0,10">
<ListBox.ItemTemplate>
<DataTemplate>
<TextBlock Text="{Binding DisplayName}" FontSize="{StaticResource PhoneFontSizeMedium}" Margin="40,0,0,0"/>
</DataTemplate>
</ListBox.ItemTemplate>
</ListBox>
I want this same operation to be done programatically.
Someone familiar to XAML to C# help me to solve this. .
It is something like this
ListBox listbox = new ListBox();
DataTemplate dataTemplate = new DataTemplate();
FrameworkElementFactory elementFactory = new FrameworkElementFactory(typeof(TextBlock));
elementFactory .SetBinding(TextBlock.TextProperty, new Binding("DisplayName"));
dataTemplate.VisualTree = elementFactory;
listbox.ItemTemplate = dataTemplate ;
If you want Programatically display the name of the peers in this list means follow #Hiệp Lê Answer.
Otherwise if you want only to get the name of the peers. Just follow this.
void SearchPeers()
{
List<string> name = new List<string>();
var peers = await PeerFinder.FindAllPeersAsync();
for(int i=0;i<peers.Count;i++)
{
string peerName = peers.DisplayName;
name.Add(peerName);
}
}
This will get you the name of the peers available.
I have a gridcontrol which is populated from database. Also, in code, I added to datatable a checkeditsettings column. I created a template in xaml , but I can't manage to convert it in C#. In my code below,
XAML code:
<dxg:GridColumn FieldName="Select" Fixed="Right" UnboundType="Boolean">
<dxg:GridColumn.EditSettings>
<dxe:CheckEditSettings />
</dxg:GridColumn.EditSettings>
<dxg:GridColumn.CellTemplate>
<DataTemplate>
<local:MyCheckEdit
IsChecked="False"
IsEnabled='True'
Checked="MyCheckEdit_Checked"
EnabledChecked="/Images/mark.png"
EnabledUnchecked="/Images/markk.png"
DisabledUnchecked="/Images/marken.png" >
</local:MyCheckEdit>
</DataTemplate>
</dxg:GridColumn.CellTemplate>
</dxg:GridColumn>
What I have tried so far:
GridColumn colselect = new GridColumn();
ComboBoxEditSettings c = new ComboBoxEditSettings();
colselect.EditSettings = c;
DataTemplate template = new DataTemplate();
template.VisualTree = new FrameworkElementFactory(typeof(MyCheckEdit));
template.VisualTree.SetBinding(MyCheckEdit.ContentProperty, new Binding("...?"));
colselect.CellTemplate = template;
I am really stack here.
Keep the DataTemplate in a Resources section in xaml, give it a name (x:Key) and just reference it from code-behind when you need it:
<dxg:DataGrid x:name="myGrid" >
<dxg:DataGrid.Resources>
<DataTemplate x:Key="MyCellTemplate" >
<local:MyCheckEdit IsChecked="False"
IsEnabled='True'
Checked="MyCheckEdit_Checked"
EnabledChecked="/Images/mark.png"
EnabledUnchecked="/Images/markk.png"
DisabledUnchecked="/Images/marken.png" />
</DataTemplate>
</dxg:DataGrid.Resources>
...
</dxg:DataGrid>
Then, in your code-behind:
GridColumn colselect = new GridColumn();
colselect.EditSettings = new ComboBoxEditSettings();
colselect.CellTemplate = myGrid.Resources["MyCellTemplate"] as DataTemplate;
I need to create a DataGridColumn from code.
The XAML equivalent would be:
<data:DataGridTemplateColumn Header="Name" Width="100">
<data:DataGridTemplateColumn.CellTemplate>
<DataTemplate>
<TextBlock Text="{Binding Name}" TextTrimming="WordEllipsis"></TextBlock>
</DataTemplate>
</data:DataGridTemplateColumn.CellTemplate>
</data:DataGridTemplateColumn>
I've started like that:
DataGridTemplateColumn column = new DataGridTemplateColumn
{
Header = "Name",
Width = 100,
};
TextBlock inside = new TextBlock {TextTrimming = TextTrimming.CharacterEllipsis};
But I don't know how to 'merge' such puzzles. There are nested elements in XAML, how to achieve this from code?
A good way to do this is to pack the entire XAML snippet into a string and call XamlReader.Load() or XamlReader.Parse() on it. The bonus feature of this approach is that it'll work in Silverlight as well (with some fiddling), where you can't build DataTemplates in code.
Almost there, change your code to this and it should work:
DataGridTemplateColumn column = new DataGridTemplateColumn
{
Header = "Name",
Width = 100,
};
FrameworkElementFactory ftb = new FrameworkElementFactory(typeof(TextBlock));
Binding b = new Binding("Name");
ftb.SetValue(TextBlock.Text, b);
ftb.SetValue(TextBlock.TextTrimming, TextTrimming.CharacterEllipsis);
DataTemplate ct = new DataTemplate();
ct.VisualTree = ftb;
column.CellTemplate = ct;
Another method besides the above is to define your datatemplate in XAML within your resources then dynamically load it in the code:
XAML:
<Window.Resources>
<DataTemplate x:Key="myCellTemplate">
<TextBlock Text="{Binding Name}" TextTrimming="WordEllipsis" />
</DataTemplate>
</Window.Resources>
Code:
DataGridTemplateColumn column = new DataGridTemplateColumn
{
Header = "Name",
Width = 100,
};
column.CellTemplate = this.FindResource("myCellTemplate") as DataTemplate;