Randy Quackers
Randy Quackers

Reputation: 715

WPF Datagrid inside other Datagrid

I am currently trying to nest a Datagrid inside another.

I am basically trying to reproduce this interface (it's not the one I have now).

enter image description here

Here is a minified version of the code used to create my interface.

<DataGrid x:Name="myDataGrid" ItemsSource="{Binding ProductsList}" x:FieldModifier="public" AutoGenerateColumns="False" Grid.Row="1">
                <DataGrid.Columns>
                    <DataGridTemplateColumn Width=".031*">
                        <DataGridTemplateColumn.HeaderTemplate>
                            <DataTemplate>
                                <StackPanel >
                                    <TextBlock Text="No. Mat" />
                                    <TextBlock Text="Format" />
                                    <TextBlock Text="No. Cas" />
                                </StackPanel>
                            </DataTemplate>
                        </DataGridTemplateColumn.HeaderTemplate>
                        <DataGridTemplateColumn.CellTemplate>
                            <DataTemplate x:Name="productFormatData">
                                <StackPanel>
                                    <TextBlock Text="{Binding MATProductNumber}" FontWeight="DemiBold" />
                                    <TextBlock Text="{Binding tblFormat.FormatName}" />
                                    <TextBlock Text="{Binding tblProduct.ProductCASNumber}" />
                                </StackPanel>
                            </DataTemplate>
                        </DataGridTemplateColumn.CellTemplate>
                    </DataGridTemplateColumn>

                    <DataGridTemplateColumn Width=".05*" >
                        <DataGridTemplateColumn.HeaderTemplate>
                            <DataTemplate>
                                <TextBlock Text="No. Lot" />
                            </DataTemplate>
                        </DataGridTemplateColumn.HeaderTemplate>
                        <DataGridTemplateColumn.CellTemplate>
                            <DataTemplate>
                                <TextBlock Text="{Binding ProductsLot}" Foreground="Black" />
                            </DataTemplate>
                        </DataGridTemplateColumn.CellTemplate>
                    </DataGridTemplateColumn>

                    <DataGridTemplateColumn Width=".055*">
                        <DataGridTemplateColumn.HeaderTemplate>
                            <DataTemplate>
                                <TextBlock Text="Actions" />
                            </DataTemplate>
                        </DataGridTemplateColumn.HeaderTemplate>
                        <DataGridTemplateColumn.CellTemplate>
                            <DataTemplate>
                                <StackPanel Orientation="Horizontal">
                                    <Button x:Name="modifyBtn" ToolTip="Modifier une fiche">
                                        <materialDesign:PackIcon Kind="Pencil" Width="25" Height="25" VerticalAlignment="Center"/>
                                    </Button>
                                    <Button x:Name="deleteBtn" ToolTip="Supprimer la fiche">
                                        <materialDesign:PackIcon Kind="Delete" Width="25" Height="25" VerticalAlignment="Center"/>
                                    </Button>
                                </StackPanel>
                            </DataTemplate>
                        </DataGridTemplateColumn.CellTemplate>
                    </DataGridTemplateColumn>

                   <DataGridTemplateColumn Width="0.1*">
                    <DataGridTemplateColumn.HeaderTemplate>
                        <DataTemplate>
                            <TextBlock Text="Dangers" />
                        </DataTemplate>
                    </DataGridTemplateColumn.HeaderTemplate>

                    <DataGridTemplateColumn.CellTemplate>
                        <DataTemplate>
                            //INSERT OTHER Datagrid HERE OR RowDetails? 
                        </DataTemplate>
                    </DataGridTemplateColumn.CellTemplate>
                </DataGridTemplateColumn>
</DataGrid>

This part is working as expected. The part that is causing me problems is the Dangers' Column (Highlighted in red in the screenshot).

Here is the code that I have tried:

<DataGridTemplateColumn Width="0.1*">
                        <DataGridTemplateColumn.HeaderTemplate>
                            <DataTemplate>
                                <TextBlock Text="Dangers" />
                            </DataTemplate>
                        </DataGridTemplateColumn.HeaderTemplate>

                        <DataGridTemplateColumn.CellTemplate>
                            <DataTemplate>
                                //INSERT OTHER Datagrid HERE OR RowDetails? 
                            </DataTemplate>
                        </DataGridTemplateColumn.CellTemplate>
                    </DataGridTemplateColumn>

I will need to bind the List DangerIcons (List of strings) in the row. It can contain from 0 to 8 dangers so I really need it to be in a row.

Basically, I have been reading on other threads and it seems to suggest to add another Datagrid inside the DataTemplate of the DataGridTemplateColumn.CellTemplate. Is that right and if so, how should I do it?

Thanks in advance!

Upvotes: 0

Views: 65

Answers (3)

Randy Quackers
Randy Quackers

Reputation: 715

I have finally resolved it, thanks to Zion Yang.

I have simply added the following ItemsControl inside the Datagrid:

<DataTemplate>
    <ItemsControl ItemsSource="{Binding TransportClassList}">
        <ItemsControl.ItemsPanel>
           <ItemsPanelTemplate>
              <StackPanel Orientation="Horizontal" Margin="5,0,0,0" />
                 </ItemsPanelTemplate>
                     </ItemsControl.ItemsPanel>

                     <ItemsControl.ItemTemplate>
                        <DataTemplate>
                            <StackPanel>
                               <Image Source="{Binding TransportIcons}" ToolTip="{Binding DangerTypeName}"  />
                            </StackPanel>
                        </DataTemplate>
                     </ItemsControl.ItemTemplate>
                  </ItemsControl>
               </DataTemplate>
         </DataGridTemplateColumn.CellTemplate>
    </DataGridTemplateColumn>
</DataTemplate>

Upvotes: 0

Zion Yang
Zion Yang

Reputation: 21

What you need is just a list of icons. I think an ItemsControl is enough. Remember set its orientation to horizontal.

Upvotes: 2

박석양
박석양

Reputation: 39

<StackPanel Orientation="Horizontal">
<Image ...   Visibility = {Binding DangerIcons ,Converter={StaticResource DangerConverter},ConverterParameter="danger1"}/>
<Image ...   Visibility = {Binding DangerIcons ,Converter={StaticResource DangerConverter},ConverterParameter="danger2"}/>
<Image ...   Visibility = {Binding DangerIcons ,Converter={StaticResource DangerConverter},ConverterParameter="danger3"}/>
<Image ...   Visibility = {Binding DangerIcons ,Converter={StaticResource DangerConverter},ConverterParameter="danger4"}/>
<Image ...   Visibility = {Binding DangerIcons ,Converter={StaticResource DangerConverter},ConverterParameter="danger5"}/>
<Image ...   Visibility = {Binding DangerIcons ,Converter={StaticResource DangerConverter},ConverterParameter="danger6"}/>
<Image ...   Visibility = {Binding DangerIcons ,Converter={StaticResource DangerConverter},ConverterParameter="danger7"}/>
</StackPanel>

You use it your way

And You must use 'Converter'

If List DangerIcons have ("Danger2","Danger3","Danger5")

 public class DangerToVisibilityConverter : MarkupExtension, IValueConverter
    {
        static DangerToVisibilityConverter convertor;

        public object Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
        {

            Type type = value.GetType();
            if (type.Equals(typeof(List<string>)))
            {
                List<string> list = value as List<string>;
                foreach(var data in list)
                {
                    if (data.Equals(parameter.ToString()))
                    {
                        return Visibility.Visible;
                    }
                }
            }

            return Visibility.Collapsed;
        }

        public object ConvertBack(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
        {
            throw new NotImplementedException();
        }

        public override object ProvideValue(IServiceProvider serviceProvider)
        {
            if (convertor == null)
            {
                convertor = new DangerToVisibilityConverter();
            }

            return convertor;
        }


        public DangerToVisibilityConverter()
        {

        }
    }

Only the element with the corresponding letter is visible.

Naturally, it must be registered in ResourceDictionary

Make ResourceDictionary

<ResourceDictionary xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
                    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
                    ...
                    xmlns:Converter="your converter'address">
    <Converter:DangerToVisibilityConverter  x:Key="DangerToVisibilityConverter "/>

</ResourceDictionary>

Then You can use Converter

Upvotes: 1

Related Questions