从代码后面获取转换属性的绑定 [英] Getting binding of transform property from code behind

查看:58
本文介绍了从代码后面获取转换属性的绑定的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我在 Grid 内部有以下代码:

 < Grid .RenderTransform> 
< TranslateTransform
X = {Binding X,Converter = {StaticResource Horizo​​ntalPositionConverter}}
Y = {Binding Y,Converter = {StaticResource VerticalPositionConverter}}
/ >
< /Grid.RenderTransform>

如何获取 TranslateTransform.X 或 TranslateTransform.Y 后面的代码?我发现了



请记住,最新的更新解决方案基于LayouTransform, -在每次单击按钮时构建视图(使其缩放)。
的问候,


I have code below inside Grid:

<Grid.RenderTransform>
    <TranslateTransform
        X="{Binding X, Converter={StaticResource HorizontalPositionConverter}}"
        Y="{Binding Y, Converter={StaticResource VerticalPositionConverter}}"
    />
</Grid.RenderTransform>

How can I get binding of TranslateTransform.X or TranslateTransform.Y in code behind? I found this question but solution works for non-nested dependency properties. What to do when they are? I cannot consider binding to entire RenderTransform. I am developing winrt app, so multibinding is out of the game.

解决方案

Here is the code behind binding. I didn't use a converter because my X and Y are defined double. In order to make a correct binding you have to use dependecy property or another notification mechanism (like INotifyPropertyChanged implementation). Here is code behind binding solution (not MVVM). I've added the button to test the moving. 1. XAML code:

<Window x:Class="TransformBindingSoHelpAttempt.MainWindow"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    Title="MainWindow" Height="350" Width="525" x:Name="This">
<Grid HorizontalAlignment="Center" VerticalAlignment="Center">
    <Grid.RenderTransform>
        <TranslateTransform
            X="{Binding ElementName=This, Path=X, UpdateSourceTrigger=PropertyChanged, Mode=TwoWay}"
            Y="{Binding ElementName=This, Path=Y, UpdateSourceTrigger=PropertyChanged, Mode=TwoWay}"/>
    </Grid.RenderTransform>
    <Button Content="Click" Width="100" Height="100" Click="ButtonBase_OnClick"></Button>
</Grid>

2. Code behind :

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

    public static readonly DependencyProperty XProperty = DependencyProperty.Register(
        "X", typeof (double), typeof (MainWindow), new PropertyMetadata(default(double)));

    public double X
    {
        get { return (double) GetValue(XProperty); }
        set { SetValue(XProperty, value); }
    }

    public static readonly DependencyProperty YProperty = DependencyProperty.Register(
        "Y", typeof (double), typeof (MainWindow), new PropertyMetadata(default(double)));

    private static double _position;

    public double Y
    {
        get { return (double) GetValue(YProperty); }
        set { SetValue(YProperty, value); }
    }

    private void ButtonBase_OnClick(object sender, RoutedEventArgs e)
    {
        X = ++_position;
        Y = _position;
    }
}

Update 1: Here is code-behind based solution, there is no binding in XAML: 3. Code behind:

    public partial class MainWindow : Window
{
    public MainWindow()
    {
        InitializeComponent();
    }



    public static readonly DependencyProperty XProperty = DependencyProperty.Register(
        "X", typeof (double), typeof (MainWindow), new PropertyMetadata(default(double)));

    public double X
    {
        get { return (double) GetValue(XProperty); }
        set { SetValue(XProperty, value); }
    }

    public static readonly DependencyProperty YProperty = DependencyProperty.Register(
        "Y", typeof (double), typeof (MainWindow), new PropertyMetadata(default(double)));

    private static double _position;

    public double Y
    {
        get { return (double) GetValue(YProperty); }
        set { SetValue(YProperty, value); }
    }

    private void ButtonBase_OnClick(object sender, RoutedEventArgs e)
    {
        X = ++_position;
        Y = _position;
    }

    private void FrameworkElement_OnLoaded(object sender, RoutedEventArgs e)
    {
        var grid = sender as Grid;
        if(grid == null) return;
        var transform = grid.RenderTransform as TranslateTransform;
        if (transform == null)
        {
            transform = InitTransformBinding();
            grid.RenderTransform = transform;
        }
        else
        {
            InitTransformBinding(transform);
        }

    }

    private TranslateTransform InitTransformBinding(TranslateTransform t = null)
    {

        var transform = t ?? new TranslateTransform();
        var xBinding = new Binding();
        xBinding.Source = this;
        xBinding.Path = new PropertyPath("X");
        xBinding.UpdateSourceTrigger = UpdateSourceTrigger.PropertyChanged;
        xBinding.Mode = BindingMode.TwoWay;
        BindingOperations.SetBinding(transform, TranslateTransform.XProperty, xBinding);
        var yBinding = new Binding();
        yBinding.Source = this;
        yBinding.Path = new PropertyPath("Y");
        yBinding.UpdateSourceTrigger = UpdateSourceTrigger.PropertyChanged;
        yBinding.Mode = BindingMode.TwoWay;
        BindingOperations.SetBinding(transform, TranslateTransform.YProperty, yBinding);
        return transform;
    }
}

4. XAML code:

<Window x:Class="TransformBindingSoHelpAttempt.MainWindow"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    Title="MainWindow" Height="350" Width="525" x:Name="This">
<Grid HorizontalAlignment="Center" VerticalAlignment="Center" Loaded="FrameworkElement_OnLoaded">
    <Button Content="Click" Width="100" Height="100" Click="ButtonBase_OnClick"></Button>
</Grid>

Update 2, here on each button click you will scale the grid. 5. Xaml code:

Window x:Class="TransformBindingSoHelpAttempt.MainWindow"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    xmlns:transformBindingSoHelpAttempt="clr-namespace:TransformBindingSoHelpAttempt"
    Title="MainWindow" Height="350" Width="525" x:Name="This">
<Window.DataContext>
    <transformBindingSoHelpAttempt:MainViewModel/>
</Window.DataContext>
<Grid HorizontalAlignment="Center" VerticalAlignment="Center">
    <ListView ItemsSource="{Binding Items}">
        <ListView.ItemContainerStyle>
            <Style TargetType="ListViewItem">
                <Setter Property="ContentTemplate">
                    <Setter.Value>
                        <DataTemplate DataType="{x:Type transformBindingSoHelpAttempt:ItemDataContext}">
                            <Grid>
                                <Grid.RenderTransform>
                                    <ScaleTransform
                                            ScaleX="{Binding X, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"
                                            ScaleY="{Binding Y, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}" />
                                </Grid.RenderTransform>
                                <Button Content="{Binding ButtonContent}" Command="{Binding ButtonCommand}"/>
                            </Grid>
                        </DataTemplate>
                    </Setter.Value>
                </Setter>
            </Style>
        </ListView.ItemContainerStyle>
    </ListView>
</Grid>

6. View models:

    public class MainViewModel:BaseObservableObject
{
    public MainViewModel()
    {
        Items = new ObservableCollection<ItemDataContext>(new List<ItemDataContext>
        {
            new ItemDataContext{ButtonContent = "A", X = 1.0, Y = 1.0},
            new ItemDataContext{ButtonContent = "B", X = 1.0, Y = 1.0},
            new ItemDataContext{ButtonContent = "C", X = 1.0, Y = 1.0},
            new ItemDataContext{ButtonContent = "D", X = 1.0, Y = 1.0},
        });
    }
    public ObservableCollection<ItemDataContext> Items { get; set; }
}

public class ItemDataContext:BaseObservableObject
{
    private ICommand _buttonCommand;
    private object _buttonContent;
    private double _x;
    private double _y;

    public double X
    {
        get { return _x; }
        set
        {
            _x = value;
            OnPropertyChanged();
        }
    }

    public double Y
    {
        get { return _y; }
        set
        {
            _y = value;
            OnPropertyChanged();
        }
    }

    public ICommand ButtonCommand
    {
        get { return _buttonCommand ?? (_buttonCommand = new DelegateCommand(Target)); }
    }

    public object ButtonContent
    {
        get { return _buttonContent; }
        set
        {
            _buttonContent = value;
            OnPropertyChanged();
        }
    }

    private void Target(object obj)
    {
        X += 0.2;
        Y += 0.2;
    }
}

7. How it is looks like:

Please keep in mind that the last update solution is based on LayouTransform and re-build the view on each button click (makes it to be scaled). Regards,

这篇关于从代码后面获取转换属性的绑定的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆