Multicolumn display combobox within WPF datagrid - wpfdatagrid

I wanted to create custom WPF datagrid control, which allows to have datagridcomboboxcolumn with multicolumn display on selection of combobox, how this can be implemented. Please help
Thanks in advance
Kartheesh.

I'm a little confused to exactly what your trying to ask, but possibly I think it's either of two things;
You want a multi-column display per column. For example you want two or more items per column displayed, e.g. two checkboxes, or textboxs, etc. The following code below displays two combox boxes binded to an object data provider
<dg:DataGridTemplateColumn >
<dg:DataGridTemplateColumn.CellTemplate>
<DataTemplate>
<StackPanel>
<TextBlock Text="{Binding item1}" />
<TextBlock Text="{Binding item2}" />
</StackPanel>
</DataTemplate>
</dg:DataGridTemplateColumn.CellTemplate>
<dg:DataGridTemplateColumn.CellEditingTemplate>
<DataTemplate>
<ComboBox ItemsSource="{StaticResource mybiglist}"
SelectedValue="{Binding item1}"/>
<ComboBox ItemsSource="{StaticResource mysecondbiglist}"
SelectedValue="{Binding item2}"/>
</DataTemplate>
</dg:DataGridTemplateColumn.CellEditingTemplate>
</dg:DataGridTemplateColumn>
Alternatively perhaps you want one or more columns per combo box, then this should help;
Multi-Column ComboBox in WPF
A Simple Multicolumn Combo Box in WPF

Related

How do I get default ComboBox behavior in a DataGridTemplate column?

In my RadDataGrid, I have to use a DataGridTemplateColumn because the Itemssource of my combobox is a collection that is a property of the object represented by the grid row. I've got it working except for the fact that the combo box is always editable. In other words, the box and dropdown arrow are always visible. In the screen shot below, the first column is a DataGridComboBoxColumn. The second is a DataGridTemplateColumn. Neither column has been clicked. (Note the column headings are not in the shot.)
In a regular combobox column on a RadDataGrid the combo box is not visible unless you double click on the column. Until you click, the column just displays the selected item. In my columns, the box and dropdown arrow are always visible, before and after you click in or out of the column.
How can I change this to the typical behavior? I want the user to have to click in the column before the box and dropdown arrow become visible. Before that, the column just display the selected item. Here is my code:
<tg:DataGridTemplateColumn SizeMode="Auto">
<tg:DataGridTemplateColumn.CellContentTemplate>
<DataTemplate>
<ComboBox Width="220"
ItemsSource="{Binding Path=ItemCategory.Items, Mode=OneWay}"
SelectedItem="{Binding Products, Mode=TwoWay}"
SelectedValue="{Binding Products.Id, Mode=OneWay}"
SelectedValuePath="Id"
DisplayMemberPath="ItemName">
</ComboBox>
</DataTemplate>
</tg:DataGridTemplateColumn.CellContentTemplate>
<tg:DataGridTemplateColumn.Header>
<TextBlock.Text = "Item Category"/>
</tg:DataGridTemplateColumn.Header>
</tg:DataGridTemplateColumn>

FlipView shows only first Items

I have some code similar to this:
<FlipView UseTouchAnimationsForAllNavigation="False" ItemsSource="{Binding Records}" SelectedItem="{Binding Record, Mode=TwoWay}">
<FlipView.ItemTemplate>
<DataTemplate x:DataType="Models:Record">
<TextBlock x:Name="debugText" Text="{x:Bind Name}" />
<UC:MyControl Record="{x:Bind Mode=OneWay, Converter={StaticResource myConverter}}" />
</DataTemplate>
</FlipView.ItemTemplate>
</FlipView>
MyControl needs the date to be converted with myConverter, and then it shows the detail information of Record. It shows an image, the name, etc.
The TextBlock debugText is created for debugging purposes.
When I move the FlipView by hand or by code, the elements are transitioning correctly. I can debug how the SelectedItem is updated correctly, and I can see the debugText updating correctly.
But for some reason, MyControl cycling between the first items. It is showing only the 3 or 4 first items, and after arriving at 3th or 4th, it starts again showing the first one. I debug the converter myConverter, and I can see that it is called 3 or 4 times loading the view. But then it not called anymore, even when I transition to the next elements.
It shows only the 3 first elements when UseTouchAnimationsForAllNavigation="False", and it shows the 4 first elements when UseTouchAnimationsForAllNavigation="True".
I can manage to show all the items correctly, by writting the FlipView.ItemsPanel:
<FlipView.ItemsPanel>
<ItemsPanelTemplate>
<StackPanel AreScrollSnapPointsRegular="True" Orientation="Horizontal" />
</ItemsPanelTemplate>
</FlipView.ItemsPanel>
But it is not a solution for me, because there are many Records (can be more than 300), and done in this way the page takes so long in loading, and wastes so much memory. When I run it in this mode in a phone, the application even crashes when there are many records.
How can I make it work for more than the 3 or 4 first items?

How to show a grid view inside a grid view?

I am developing a windows 8 app. And I want to display a GridView inside of another GridView item template. And I have added a visibility binding to the inner GridView, but the binding doesn't work when wrapping the GridViewItems in the outer GridView. It works when i use a simple ListView or GridView without any wrapping.
This is the main GridView with wrapping
<GridView
Name="feedGridView"
Background="Transparent"
SelectionMode="None"
ItemTemplate="{StaticResource MyFeedGridView}">
<GridView.ItemsPanel>
<ItemsPanelTemplate>
<VariableSizedWrapGrid Height="600" Orientation="Vertical" />
</ItemsPanelTemplate>
</GridView.ItemsPanel>
</GridView>
The style for "MyFeedGridView" which contains another GridView
<DataTemplate x:Key="MyFeedGridView">
<Grid HorizontalAlignment="Left" Width="500">
<StackPanel x:Name="gridViewStackPanel" Orientation="Horizontal" >
<GridView
HorizontalAlignment="Right"
x:Name="myFeedGridViewInListView"
ItemTemplate="{StaticResource MyFeedGridViewInListView}"
ItemsSource="{Binding listContent}"
Height="100"
Visibility="{Binding listContent,Converter={StaticResource FeedListToVisibilityConverter}}"
SelectionMode="None"
Width="400" />
</StackPanel>
</Grid>
</DataTemplate>
I am using a converter to hide or show the inner GridView. The below is the converter that i am using
public object Convert(object value, Type targetType, object parameter, string language)
{
List<ContentList> contents = value as List<ContentList>;
return (contents != null && contents.Count > 0) ? Visibility.Visible : Visibility.Collapsed;
}
My problem is that the inner GridView gets hidden for all the items or gets visible for all the items irrespective of the listcontent that I have bound.
I have noticed is that this is happening only when I set the ItemsPanel. If I remove the VariableSizedWrapGrid property then it's working as expected. But I need to wrap the items after each column so I can't do away with it.
Please let me know if you have any clue why this is happening.
Thanks
EDIT:
Attaching image of how the grid view items should be arranged. If you see the first item of the grid view, it has another grid view inside the grid view item representing songs. So this inner grid view will be empty for some items and populated for some. So I had written a visibility converter to show and hide the inner grid view. And when am using the converter,if the first grid view item has inner grid view items(songs then it will show inner grid view for all the items and if the first grid view item doesnt have any inner grid view items(songs) then it hides inner grid view for all the main grid view items.
Let me know if its not clear.
The problem with a GridView is that it uses the same size for all its GridViewItems by default. You can use a VariableSizedWrapGrid as its ItemsPanel, but that will disable virtualization and so you won't be able to use your GridView with a large number of items (more than a few dozen) without incurring performance cost.
For your scenario you could use a GridView with a non-uniform ItemsSource - one where some items represent the main list item and some that represent lists of songs and use the ItemTemplateSelector to specify which template to use for which type of item. It's not ideal of course, but this is what your easiest option is. One problem is that some of these song lists might end up orphaned in a different column than the item they are associated with, so for the ugly workaround you might need to figure out the number of items per column and in the list also include empty items or rearrange the items so that the empty-end-of-column items are filled with items that don't have any song lists associated with them.
A better option might be to use a VariableSizedWrapGrid as ItemsSource or simply use a manually populated Grid and add a more... item at the end that opens a ListView, since vertical lists IMHO are easier to scroll than horizontal GridViews. You would still need to use a non-uniform ItemsSource and ItemTemplateSelector to get the desired layout and keep virtualization of the list, but that's what you get.

ComboBox which is bound to a db table should initially be blank

I have a WPF combobox control bound to a edm field in a database table. This works fine except that it enters the first value in the control when it starts which is not wanted. Heres the xaml
<ComboBox x:Name="cbMeasure"
Width="104"
ItemsSource="{Binding Source={StaticResource ddMeasureViewSource}}"
DisplayMemberPath="Measure"
IsSynchronizedWithCurrentItem="True"
SelectedValuePath="Measure"
SelectedValue="{Binding Measure1}"/>
If I just hard code the control it doesn't put the first value in the variable. Heres what that xaml looks like
<ComboBox x:Name="cbMeasure" Width="104" Text="{Binding Measure1}">
<TextBlock Text="one"/>
<TextBlock Text="two"/>
<TextBlock Text="three"/>
<TextBlock Text="four"/>
</ComboBox>
What do I have to do to make the database bound combobox start with an empty value the way the textbox combobox does? This is a problem as it puts the first value in the SelectedValue bound to a variable (Measure1).
The db table ddMeasure looks like:
RID Measure
--- -------
1 One
2 Two
3 Three
4 Four
so "One" in put into the ComboBox selection and Measure1 variable is populated as well.
OK I found the solution to this. You have to set the property IsSynchronizedWithCurrentItem to false which I thought I had tried but I think I just removed that property and the default must be true. So the xaml looks like
<ComboBox x:Name="cbMeasure"
Width="104"
ItemsSource="{Binding Source={StaticResource ddMeasureViewSource}}"
DisplayMemberPath="Measure"
IsSynchronizedWithCurrentItem="False"
SelectedValuePath="Measure"
SelectedValue="{Binding Measure1}"/>
Hope this helps others who try to find info on this type of binding.

How to make a cell in a datagrid readonly based the content on another cell in SL4?

I have two columns, the second column depends on the content on the first column. By default, the second columns is readonly. When I enter some valid value, I want the second column to become editable.
To achive this, I created a cell template and cell edit template on the second column where back ground and read only bound to the first column. On load, the first column is null so my second columns comes correctly as read only. Following is Cell Template for second column, where the background color is set by based on the first column.
<DataTemplate>
<Grid>
<Border Background="{Binding FristColumn,Converter={StaticResource ColorConverter}}"/>
<TextBlock Text="{Binding SecondColumn, Converter={StaticResource NumberFormatter}}" HorizontalAlignment="Stretch" VerticalAlignment="Center" Margin="0"/>
</Grid>
</DataTemplate>
Following is cell edit template for second column to make it editable
<DataTemplate>
<Grid>
<TextBox Text="{Binding SecondColumn, Mode=TwoWay, Converter={StaticResource NumberFormatter}}" Margin="0" HorizontalAlignment="Right" IsReadOnly="{Binding FirstColumn, Converter={StaticResource readOnlyConverter}, ConverterParameter=FirstColumn}" Background="{Binding Depend,Converter={StaticResource ColorConverter}, ConverterParameter=FirstColumn}" />
</Grid>
</DataTemplate>
With these two in place, when enter the valid value in the first column, I was expecting the second column color to change but it does not. But If I double click on the cell then it behaves properly based on the first cell. Is there some thing I am missing?
The problem was, the object collection did not have INotifyPropertyChanged implemented. Once I have INotifyPropertyChanged implemented, the colors and cell become editable and non editable based on the converter.
Hope this helps others.