Comment puis-je associer des données à une largeur de ColumnDefinition ou à une hauteur de RowDefinition?

StackOverflow https://stackoverflow.com/questions/147908

Question

Sous le modèle View-Model-ViewModel pour WPF, j'essaie de rechercher les hauteurs et les largeurs de différentes définitions pour les contrôles de grille afin de pouvoir stocker les valeurs définies par l'utilisateur après l'utilisation d'un GridSplitter. Cependant, le schéma normal ne semble pas fonctionner pour ces propriétés particulières.

Remarque: je poste cette question en tant que question de référence, car Google m'a échoué et j'ai dû résoudre ce problème moi-même. Ma propre réponse à suivre.

Était-ce utile?

La solution 2

J'ai découvert un certain nombre de pièges:

  1. Bien que cela puisse apparaître comme un double en XAML, la valeur réelle de la hauteur ou de la largeur d'une définition est une structure 'GridLength'.
  2. Toutes les propriétés de GridLength sont en lecture seule. Vous devez en créer une chaque fois que vous le modifiez.
  3. Contrairement à toutes les autres propriétés de WPF, Width et Height ne définissent pas leur mode de liaison de données sur "TwoWay", vous devez le définir manuellement.

Ainsi, j'ai utilisé le code suivant:

private GridLength myHorizontalInputRegionSize = new GridLength(0, GridUnitType.Auto)
public GridLength HorizontalInputRegionSize
{
    get
    {
        // If not yet set, get the starting value from the DataModel
        if (myHorizontalInputRegionSize.IsAuto)
            myHorizontalInputRegionSize = new GridLength(ConnectionTabDefaultUIOptions.HorizontalInputRegionSize, GridUnitType.Pixel);
        return myHorizontalInputRegionSize;
    }
    set
    {
        myHorizontalInputRegionSize = value;
        if (ConnectionTabDefaultUIOptions.HorizontalInputRegionSize != myHorizontalInputRegionSize.Value)
        {
            // Set the value in the DataModel
            ConnectionTabDefaultUIOptions.HorizontalInputRegionSize = value.Value;
        }
        OnPropertyChanged("HorizontalInputRegionSize");
    }
}

Et le XAML:

<Grid.RowDefinitions>
    <RowDefinition Height="*" MinHeight="100" />
    <RowDefinition Height="Auto" />
    <RowDefinition Height="{Binding Path=HorizontalInputRegionSize,Mode=TwoWay}" MinHeight="50" />
</Grid.RowDefinitions>

Autres conseils

Créez un IValueConverter comme suit:

public class GridLengthConverter : IValueConverter
{
    public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
    {
        double val = (double)value;
        GridLength gridLength = new GridLength(val);

        return gridLength;
    }

    public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture)
    {
        GridLength val = (GridLength)value;

        return val.Value;
    }
}

Vous pouvez ensuite utiliser le convertisseur dans votre liaison:

<UserControl.Resources>
    <local:GridLengthConverter x:Key="gridLengthConverter" />
</UserControl.Resources>
...
<ColumnDefinition Width="{Binding Path=LeftPanelWidth, 
                                  Mode=TwoWay,
                                  Converter={StaticResource gridLengthConverter}}" />

Une autre possibilité, puisque vous avez évoqué la conversion entre GridLength et int , consiste à créer un IValueConverter et à l'utiliser pour la liaison à Largeur . IValueConverter gère également la liaison bidirectionnelle car il existe à la fois les méthodes ConvertTo () et ConvertBack () .

La solution la plus simple consiste à utiliser simplement les paramètres de chaîne pour ces propriétés afin que WPF les prenne automatiquement en charge à l’aide de GridLengthConverter, sans aucun travail supplémentaire.

Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top