none
How do you synchronize the moving of UIElement to RenderTransform's TranslateTransform?

    Question

  • I build a Window with an InkCanvas containing a TextBlock. 
    I add a TranslateTransform to that UIElement on initialization. 
    I move the TextBlock with the mouse. 

    I would expect the TranslateTransform (assigned to RenderTransform) to be updated based on the new location, but it's not.  How do I make this happen?  Am I going about this wrong?

    I need to have it updated because if later I try to move that element programmatically, weird things happen...ie it doesn't end up where I expect it to.

    Thanks for your time

    <Window x:Class="UnchangingTransforms.Window1"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        Title="Window1" Height="437.5" Width="421.25">
        <Grid>
            <InkCanvas Name="inkcanvas" EditingMode="Select" RenderTransformOrigin="0,0" Margin="12,12,12,45">
                <TextBlock Name="textBlock1" Text="WPF TextBlock" Height="44" Width="222" />
        </InkCanvas>
        <Button Height="31.25" Margin="156.25,0,158.75,7.5" Name="button1" VerticalAlignment="Bottom" Click="button1_Click">Button</Button>
        </Grid>
    </Window>
    
    using System;
    using System.Windows;
    using System.Windows.Controls;
    using System.Windows.Media;
    
    namespace UnchangingTransforms
    {
    	public partial class Window1 : Window
    	{
    		public Window1()
    		{
    			InitializeComponent();
    			addElement();
    		}
    
    		private void addElement()
    		{
    			TextBlock block = new TextBlock();
    			block.Text = "testBlock";
    			inkcanvas.Children.Add(block);
    			block.RenderTransform = new TranslateTransform(222, 221);
    		}
    
    		private void button1_Click(object sender, RoutedEventArgs e)
    		{
    			TranslateTransform tt = (TranslateTransform) inkcanvas.Children[1].RenderTransform;
    			Console.WriteLine(tt.X + ", " + tt.Y);
    		}
    
    	}
    }
    

     

    Tuesday, December 15, 2009 7:18 AM

Answers

  • Hi,

    Thanks for the clarification. Now let me try again.

    First, I don't think we need the TranslateTransform here to position the TextBlock, instead, just set the Left/Top attached property will do:

    TextBlock block = new TextBlock();
    
    block.Text = "testBlock";
    inkcanvas.Children.Add(block);
    InkCanvas.SetLeft(block, 222);
    InkCanvas.SetTop(block, 221);
    

    And now if you click the added TextBlock, you'll see it is surrounded by a resizing adorner like this:

    TextBlock on InkCanvas

    Now move your mouse cursor onto the adorner border, you automatically have the correct move/resize behavior.

    Is that what you want?

    Thanks,
    Jie
    MSDN Subscriber Support in Forum
    If you have any feedback on our support, please contact msdnmg@microsoft.com
    Please remember to mark the replies as answers if they help and unmark them if they provide no help.

    If you have any feedback, please tell us.

    The CodeFx Project
    My Blog (in Simplified Chinese)
    • Marked as answer by usabilitytank Friday, December 18, 2009 8:17 AM
    Thursday, December 17, 2009 9:38 AM

All replies

  • Hi,

    I don't quite understand what you're trying to do.... So can you help clarify the following questions?

    What do you mean by "I move the TextBlock with the mouse"?

    After the window is loaded, you have two TextBlock elements - one defined in Xaml, one added in the addElement method - which one do you want to move?

    How do you want to move the TextBlock? Follow the mouse cursor (no need to press a mouse button) or the drag & drop style?

    Thanks,
    Jie
    MSDN Subscriber Support in Forum
    If you have any feedback on our support, please contact msdnmg@microsoft.com
    Please remember to mark the replies as answers if they help and unmark them if they provide no help.

    If you have any feedback, please tell us.

    The CodeFx Project
    My Blog (in Simplified Chinese)
    Tuesday, December 15, 2009 12:56 PM
  • Jie, I apologize for not being more clear.

    My question applies to the TextBlock added in addElement() and is labeled "testBlock".  After adding it I immediately move it by assigning, in code, a TranslateTransform to its RenderTransform property (it's translated to 222,221):

       block.RenderTransform = new TranslateTransform(222, 221);

    Now if I drag that TextBlock manually (with my mouse) to a new position on the canvas, the TranslateTransform remains as it was originally assigned, at 222,221.  My first expectation was that WPF (or the InkCanvas or something) would update the TranslateTransform to the new location, but it doesn't.  So do I have to manually change that Transform to reflect the UIElement's new location?  If so, how and when should I do that?

    (The Xaml TextBlock was just left over from trying other things, so it should be ignored.  The button was just to confirm that, after trying to move the element with the mouse, the TranslateTransform was not updated to the new position.)

    Thanks
    Tuesday, December 15, 2009 2:55 PM
  • Hi,

    Thanks for the clarification. Now let me try again.

    First, I don't think we need the TranslateTransform here to position the TextBlock, instead, just set the Left/Top attached property will do:

    TextBlock block = new TextBlock();
    
    block.Text = "testBlock";
    inkcanvas.Children.Add(block);
    InkCanvas.SetLeft(block, 222);
    InkCanvas.SetTop(block, 221);
    

    And now if you click the added TextBlock, you'll see it is surrounded by a resizing adorner like this:

    TextBlock on InkCanvas

    Now move your mouse cursor onto the adorner border, you automatically have the correct move/resize behavior.

    Is that what you want?

    Thanks,
    Jie
    MSDN Subscriber Support in Forum
    If you have any feedback on our support, please contact msdnmg@microsoft.com
    Please remember to mark the replies as answers if they help and unmark them if they provide no help.

    If you have any feedback, please tell us.

    The CodeFx Project
    My Blog (in Simplified Chinese)
    • Marked as answer by usabilitytank Friday, December 18, 2009 8:17 AM
    Thursday, December 17, 2009 9:38 AM
  • Thanks, Jie!  That solved the problem of the weird behavior....until I tried another TranlsateTransform later.  Is there a way to "apply then remove" a TranslateTransform so that it keeps the results of the transformation, but doesn't interfere later?  I may be able to get rid of TranslateTransforms altogether, but if there's a way to apply the effects and then get rid of it, that would be interesting.  My gut tells me I may not be working with this stuff as it was designed. 

    Friday, December 18, 2009 8:27 AM
  • Can you let me know why are you using the TranslateTransform instead of just setting the Left/Top attached properties?

    Thanks,
    Jie
    MSDN Subscriber Support in Forum
    If you have any feedback on our support, please contact msdnmg@microsoft.com
    Please remember to mark the replies as answers if they help and unmark them if they provide no help.

    If you have any feedback, please tell us.

    The CodeFx Project
    My Blog (in Simplified Chinese)
    Friday, December 18, 2009 10:11 AM
  • We're trying to provide all types of functionality to the user for strokes and UI elements (and background image): Scale, Rotate, Movement (with undo/redo).  I just thought Transforms were the way to accomplish this in WPF.  As you probably realize, I am new to the WPF/InkCanvas, etc.  I have read quite a bit on it by now, and have the [possibly incorrect] impression that setting actual x,y coordinates was not the preferred method of placing UI elements and strokes.  Should I avoid TranslateTransforms?  Under certain circumstances?  I guess that's what I'm struggling with: when and when not to use them. 

    So now it seems apparent that when I move an object with SetLeft and SetTop, WPF is NOT creating some underlying TranslateTransform with that object.  So should I only use the ScaleTransform and RotateTransform?  Or are there better options for those types of functionality as well?

    Thanks for you responses, Jie!

    Spencer

    Monday, December 21, 2009 9:15 PM
  • Hi Spencer,

    It depends whether or not setting (X,Y) coordinates is a good practice to layout the UI elements.

    In your case, it sounds like to me the scenario is close to a painting application, and since you're working on an InkCanvas, it is definitely okay to set an element's Left/Top attached properties. The TranslateTransform class is especially useful for moving elements inside panels that do not support absolute positioning. So you don't need to use the TranslateTransform here. And of course, when you move the element on the InkCanvas, the element's actual Top/Left attached properties' values will change, WPF won't automatically create a TranslateTransform.

    For rotation and scaling, you could probably make use of the related transforms. If you have any questions, you can create new threads for each topic, the community and our team will be helping you.

    Regards,
    Jie
    MSDN Subscriber Support in Forum
    If you have any feedback on our support, please contact msdnmg@microsoft.com
    Please remember to mark the replies as answers if they help and unmark them if they provide no help.

    If you have any feedback, please tell us.

    The CodeFx Project
    My Blog (in Simplified Chinese)
    Friday, December 25, 2009 10:30 AM