Как да зададете стил за GridView клетки

Озадачен съм как просто да подравня някои колони в GridView, без да пиша тонове маркиране за всяка колона.

Не мога да използвам статичен CellTemplate, защото шаблоните на клетки се игнорират, когато зададете DisplayMemberBinding едновременно (вижте забележки в MSDN). Без DisplayMemberBinding щях да се върна към един персонализиран шаблон на клетка на колона, защото обвързването е различно и това е, което искам да избегна.

Така че би бил страхотен стил, който можем да използваме за заглавката:

<GridViewColumn DisplayMemberBinding="{Binding Bla}" HeaderContainerStyle="{StaticResource RightAlignStyle}" />

Въпреки това не мога да намеря свойство за задаване на стил за клетъчни елементи.

Сигурно ми липсва гората сред дърветата...


person realMarkusSchmidt    schedule 14.11.2011    source източник
comment
Здравейте, колони от какви типове използвате - само DataGridTextBoxColumns?   -  person    schedule 14.11.2011
comment
Ето подобен, чудя се дали е от помощ: stackoverflow.com/questions/3652318/ datagrid-text-alignment   -  person    schedule 14.11.2011
comment
@Dmitry, в този случай е само за четене, така че използвам TextBlock. Много просто, затова искам да избегна персонализирани CellTemplates за много колони.   -  person realMarkusSchmidt    schedule 14.11.2011
comment
По отношение на другия SO въпрос, който споменахте: Изглежда, че това решение няма да ми позволи да задам подравняване на колона, само за цялата мрежа. От друга страна, аз просто драскам повърхността на това, което е възможно с WPF, така че може би пропускам нещо очевидно. Все пак много благодаря!   -  person realMarkusSchmidt    schedule 14.11.2011
comment
WPF ListView няма концепция за cell. Препоръчвам да използвате много по-добър контрол на потребителския интерфейс, т.е. DataGrid за това.   -  person WPF-it    schedule 14.11.2011
comment
AngelWPF - Нито DataGrid.   -  person    schedule 14.11.2011
comment
@AngelWPF, не знам какво имаш предвид под липса на концепция за клетка. За всяка колона има заглавка и елементи (или клетки). Има GridViewColumn.HeaderTemplate и GridViewColumn.CellTemplate. Относно DataGrid: Тъй като имам нужда от това само за показване, а не за редактиране, предпочетох ListView, за да го поддържам постно (но не знам дали това предположение всъщност има смисъл).   -  person realMarkusSchmidt    schedule 14.11.2011
comment
@Дмитрий, не съм съгласен. DataGrid има ясно дефиниран и идентифициран обект на съдържание, наречен DataGridCell. ListView не го прави. @markus, ListView.CellTemplate е основно логическа концепция за това какъв шаблон ще бъде представен под колона на всеки ред. За съжаление не съответства на cell, тъй като ListView няма такъв обект, наречен ListViewCell   -  person WPF-it    schedule 15.11.2011


Отговори (2)


Маркъс, ето какво бих направил. Захапете куршума и на цената на писане на 10 реда код си осигурете първокласна поддръжка за подравнявания и всякакви други неподдържани свойства. можете да прекосите визуалното дърво и да потърсите PART_* нещо за тежката фина настройка.

Решението е:

1. Клас на подравняваща се колона:

namespace AlignableCellsProject
{
    public class AlignableTextColumn: DataGridTextColumn
    {
        protected override System.Windows.FrameworkElement GenerateElement(DataGridCell cell, object dataItem)
        {
            FrameworkElement element = base.GenerateElement(cell, dataItem);
            element.SetValue(FrameworkElement.HorizontalAlignmentProperty, this.HorizontalAlignment);

            return element;
        }

        protected override System.Windows.FrameworkElement GenerateEditingElement(DataGridCell cell, object dataItem)
        {
            FrameworkElement element = base.GenerateEditingElement(cell, dataItem);
            element.SetValue(FrameworkElement.HorizontalAlignmentProperty, this.HorizontalAlignment);

            return element;
        }

        public HorizontalAlignment HorizontalAlignment
        {
            get { return (HorizontalAlignment)this.GetValue(FrameworkElement.HorizontalAlignmentProperty); }
            set { this.SetValue(FrameworkElement.HorizontalAlignmentProperty, value); }
        }
    }
}

2. XAML на потребителя:

<Window x:Class="AlignableCellsProject.MainWindow"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:local="clr-namespace:AlignableCellsProject"
        Title="MainWindow" Height="350" Width="525">
    <Grid>
        <DataGrid x:Name="g" AutoGenerateColumns="False">
            <DataGrid.Columns>
                <local:AlignableTextColumn HorizontalAlignment="Left"
                                           Width="200" Binding="{Binding}"/>
            </DataGrid.Columns>
        </DataGrid>
    </Grid>
</Window>

3 - Код на потребителя зад:

namespace AlignableCellsProject
{
    /// <summary>
    /// Interaction logic for MainWindow.xaml
    /// </summary>
    public partial class MainWindow : Window
    {
        public MainWindow()
        {
            InitializeComponent();

            this.Loaded += 
                (o, e) => 
                {
                    this.g.ItemsSource = Enumerable.Range(1, 3);
                };
        }
    }
}

person Community    schedule 14.11.2011
comment
Благодаря ви много за труда! Интересен подход, ще го пробвам. Може би дори мога да разширя това, за да позная правилното подравняване въз основа на типа на обвързаното свойство (напр. числово -> подравняване вдясно, текст -> подравняване вляво). - person realMarkusSchmidt; 14.11.2011
comment
Това несъмнено е интересна корекция! - person ; 14.11.2011

Не използвам .Net 4.0, но това служи на целта...

   <tk:DataGrid ItemsSource="{Binding}" IsReadOnly="True" AutoGenerateColumns="True">
        <tk:DataGrid.Resources>
            <Style x:Key="MyAlignedColumn" TargetType="{x:Type tk:DataGridCell}">
                <Setter Property="HorizontalAlignment" Value="Right"/>
                <Setter Property="HorizontalContentAlignment" Value="Left"/>
            </Style>
        </tk:DataGrid.Resources>
        <tk:DataGridTextColumn Header="Name"
                               CellStyle="{StaticResource MyAlignedColumn}"
                               Binding="{Binding Name, Mode=TwoWay}"/>
    </tk:DataGrid>
person WPF-it    schedule 15.11.2011
comment
+1, използвал съм това. За да добавим към това, ако искаме определена колона да показва подравняване, тогава можем да зададем DataGridColumn.CellStyle={StaticResource CellAlignmentStyle}, където CellAlignmentStyle е ключът, присвоен на стила по-горе. - person ; 15.11.2011
comment
Въпросът беше за ListView с GridView, а не DataGrid. - person Olly; 26.03.2014