This is a migrated thread and some comments may be shown as answers.

How to display DataGrid Column header in 2 lines?

3 Answers 156 Views
This is a migrated thread and some comments may be shown as answers.
Scott
Top achievements
Rank 1
Scott asked on 18 Apr 2018, 12:04 PM

Unable to find anything on the Xamarin Forms UI forum that solves this,
have looked at this - https://www.telerik.com/forums/several-xamarin-datagrid-questions
and this on the UI for Windows forum - https://www.telerik.com/forums/how-to-display-datagrid-column-header-in-2-lines
I've tried using a DataGridTemplateColumn:

<grid:DataGridTemplateColumn CanUserEdit="False"
                             HeaderText="Title">
    <grid:DataGridTemplateColumn.HeaderContentTemplate>
        <DataTemplate>
            <Grid>
                <Grid.RowDefinitions>
                    <RowDefinition Height="Auto" />
                    <RowDefinition Height="Auto" />
                </Grid.RowDefinitions>
 
                <Label Text="Distance" />
                <Label Text="(miles)" Grid.Row="1" />
            </Grid>
        </DataTemplate>
    </grid:DataGridTemplateColumn.HeaderContentTemplate>
    <grid:DataGridTemplateColumn.CellContentTemplate>
        <DataTemplate>
            <Grid>
                <Label Text="{Binding JourneyDistance}" />
            </Grid>
        </DataTemplate>
    </grid:DataGridTemplateColumn.CellContentTemplate>
</grid:DataGridTemplateColumn>

Which returns - No property, bindable property, or event found for 'CellContentTemplate', or mismatching type between value

Also tried a DataGridTextColumn.HeaderContentTemplate using both a StackLayout

<grid:DataGridTextColumn CanUserEdit="False"
                         PropertyName="JourneyDistance">
    <grid:DataGridTextColumn.HeaderContentTemplate>
        <DataTemplate>
            <StackLayout>
                <Label Text="Line 1" />
                <Label Text="Line 2" />
            </StackLayout>
        </DataTemplate>
    </grid:DataGridTextColumn.HeaderContentTemplate>
</grid:DataGridTextColumn>

 

and a Grid inside the template

<grid:DataGridTextColumn CanUserEdit="False"
                         PropertyName="JourneyDistance">
    <grid:DataGridTextColumn.HeaderContentTemplate>
        <DataTemplate>
            <Grid>
                <Grid.RowDefinitions>
                    <RowDefinition Height="Auto" />
                    <RowDefinition Height="Auto" />
                </Grid.RowDefinitions>
 
                <Label Text="Distance" />
                <Label Text="(miles)" Grid.Row="1" />
            </Grid>
        </DataTemplate>
    </grid:DataGridTextColumn.HeaderContentTemplate>
</grid:DataGridTextColumn>

The last snippet runs without error but the header is just empty

Help please.

3 Answers, 1 is accepted

Sort by
0
Lance | Manager Technical Support
Telerik team
answered on 18 Apr 2018, 04:14 PM
Hello Scott,

Thank you for sharing the code, I have built you a demo (attached) that shows how to use your HeaderContentTemplate, in conjunction with DataGridHeaderStyle, to get the desired a multi-line column header:



<grid:DataGridTextColumn CanUserEdit="False"
                         HeaderText="Distance"
                         PropertyName="JourneyDistance">
    <grid:DataGridTextColumn.HeaderStyle>
        <grid:DataGridColumnHeaderStyle TextMargin="2"  />
    </grid:DataGridTextColumn.HeaderStyle>
    <grid:DataGridTextColumn.HeaderContentTemplate>
        <DataTemplate>
            <Grid>
                <Grid.RowDefinitions>
                    <RowDefinition Height="Auto" />
                    <RowDefinition Height="Auto" />
                </Grid.RowDefinitions>
 
                <Label Text="Distance" />
                <Label Text="(miles)"
                       Grid.Row="1" />
            </Grid>
        </DataTemplate>
    </grid:DataGridTextColumn.HeaderContentTemplate>
</grid:DataGridTextColumn>


You'll see that the HeaderStyle object provides you with a lot of options to customize the header's appearance:




If you have any further trouble, please open a support ticket and attach the problematic code so that we can investigate further.

Regards,
Lance | Tech Support Engineer, Sr.
Progress Telerik
Do you want to have your say when we set our development plans? Do you want to know when a feature you care about is added or when a bug fixed? Explore the Telerik Feedback Portal and vote to affect the priority of the items
0
Scott
Top achievements
Rank 1
answered on 20 Apr 2018, 12:13 PM

Hi Lance

Thanks for your help here,

Ultimately your solution was correct although I ended up loosing a few hours productivity because the text colour decided to default to white (facepalm), so finally I ended up with:

<grid:DataGridTextColumn CanUserEdit="False"
                HeaderText="Distance"
                PropertyName="SomeProperty">
    <grid:DataGridTextColumn.HeaderStyle>
        <grid:DataGridColumnHeaderStyle TextMargin="2" />
    </grid:DataGridTextColumn.HeaderStyle>
    <grid:DataGridTextColumn.HeaderContentTemplate>
        <DataTemplate>
            <Grid>
                <Grid.RowDefinitions>
                    <RowDefinition Height="Auto" />
                    <RowDefinition Height="Auto" />
                </Grid.RowDefinitions>
 
                <Label Margin="4,4,4,0"
                    Text="Line 1"
                    TextColor="{StaticResource ColourGridHeaderText}" />
                <Label Margin="4,0,4,4"
                    Text="Line 2"
                    TextColor="{StaticResource ColourGridHeaderText}"
                    Grid.Row="1" />
            </Grid>
        </DataTemplate>
    </grid:DataGridTextColumn.HeaderContentTemplate>
</grid:DataGridTextColumn>

 

On a separate note the heading row is now a little uneven in height, see attached,

how would I go about making the header a consistent height that is also scalable?

0
Accepted
Lance | Manager Technical Support
Telerik team
answered on 20 Apr 2018, 03:28 PM
Hi Scott,

I'm not able to replicate this on my side with the amount of code I have, but my answer would likely be the same in any case.

This is due to the margins on the template's child elements and the reduced header height ?. Although you've set a zero margin for the top and bottom Labels, there is still 8px in the middle plus the 4px (2+2) TextMargin set in the style.

I recommend start with no margins and then gradually increment until you push out the parent container, that'll be your limit.

If you have to a larger header, you can move your HeaderStyle to a resource and share it across all the columns so that the appearance is consistent.

<ContentPage.Resources>
    <ResourceDictionary>
        <grid:DataGridColumnHeaderStyle x:Key="MyColumnHeaderStyle" TextMargin="2"   />
    </ResourceDictionary>
</ContentPage.Resources>


<grid:RadDataGrid x:Name="DataGrid"
                  AutoGenerateColumns="False">
    <grid:RadDataGrid.Columns>
        <grid:DataGridTextColumn PropertyName="Destination"
                         CanUserEdit="False"
                         HeaderText="Destination"
                         HeaderStyle="{StaticResource MyColumnHeaderStyle}"/>
        <grid:DataGridTextColumn CanUserEdit="False"
                         HeaderText="Distance"
                         PropertyName="JourneyDistance"
                         HeaderStyle="{StaticResource MyColumnHeaderStyle}">
            <grid:DataGridTextColumn.HeaderContentTemplate>
                ...
            </grid:DataGridTextColumn.HeaderContentTemplate>
        </grid:DataGridTextColumn>
    </grid:RadDataGrid.Columns>
</grid:RadDataGrid>


As far as the text scaling with the display, you could use a Xamarin.Forms FontSize enum which will provide the appropriate font size for the device and screen. See the Xamarin.Forms Fonts article for more information. Here's a quick example:

<Label FontSize="Large"/>
<Label FontSize="Small"/>

Alternatively, you could try using a Xamarin.Forms text Style: which also adapts to the device.

<Label Text="Check out my style." Style="{StaticResource LabelStyle}" />

Worst case scenario, if you need a finer level of control, you could hook into the ContentPage SizeChanged event and dynamically set the things you want larger:

private void StartPage_OnSizeChanged(object sender, EventArgs e)
{
    var page = sender as ContentPage;
 
    var isLarge = page.Height > 600;
 
    if (isLarge)
    {
        // make things larger
    }
    else
    {
        // make things smaller
    }
}


Regards,
Lance | Tech Support Engineer, Sr.
Progress Telerik
Do you want to have your say when we set our development plans? Do you want to know when a feature you care about is added or when a bug fixed? Explore the Telerik Feedback Portal and vote to affect the priority of the items
Asked by
Scott
Top achievements
Rank 1
Answers by
Lance | Manager Technical Support
Telerik team
Scott
Top achievements
Rank 1
Share this question
or