Thứ hai, ngày 5 tháng 12 năm 2016

WPF – 2D Transformations

Ngày đăng: 28/3/2012, 9:5:29AM | Lượt xem: 6,355
Hot!

Để thiết kế được một giao diện vừa ý, đôi lúc bạn cần đến các kĩ thuật biến đổi các đối tượng đồ họa. Trong WPF, bạn có thể thực hiện điều này với các lớp Transform bao gồm: Translate, Rotate, Scale, Skew và Matrix.

WPF - Rotate TransformĐể thiết kế được một giao diện vừa ý, đôi lúc bạn cần đến các kĩ thuật biến đổi các đối tượng đồ họa. Trong WPF, bạn có thể thực hiện điều này với các lớp Transform bao gồm: Translate, Rotate, Scale, Skew và Matrix.


Download demo+sourcecode (213KB)

Giới thiệu

Có tất cả 5 loại Transform mà tôi đã liệt kê ở trên. Tất cả các Transform này đều có lớp tương ứng trong .Net theo tên gọi của nó và đều được kế thừa từ lớp abstract Transform:

WPF - Transform Hierarchy Diagram

  • TranslateTransform: thay đổi tọa độ của đối tượng (đồ họa) thông qua hai property là X và Y.
  • RotateTransform: xoay đối tượng theo một góc Angle với tâm xác định bởi CenterX và CenterY.
  • ScaleTransform: co giãn kích thước của đối tượng theo tỉ lệ với ScaleX, ScaleY và tâm CenterX, CenterY.
  • SkewTransform: làm xiên đối tượng với góc AngleX, AngleY và tâm CenterX, CenterY.
  • MatrixTransform: thực hiện các phép biến đổi đồ họa với ma trận.

Để tạo Transform, bạn chỉ cần gán giá trị cho property UIElement. RenderTransform cho một thể hiện của các lớp trên. Trong trường hợp cần kết hợp nhiều loại Transform, bạn hãy đọc TransformGroup ở cuối của bài viết.

Tôi sẽ lần lượt giới thiệu ví dụ về từng loại Transform trên ngoại trừ MatrixTransform. Lớp này sẽ được tôi dành lại trong bài khác. Với mỗi ví dụ Transform, tôi tạo một UserControl và thêm tất cả vào một TabControl trong MainForm.

TranslateTransform

<UserControl x:Class="TranformationsDemo.TranslateTransformPanel"
             xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
             xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
             xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
             xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
             mc:Ignorable="d"
             d:DesignHeight="262" d:DesignWidth="409">
    <DockPanel LastChildFill="True">
        <StackPanel DockPanel.Dock="Left" Width="150" Margin="5">
            <StackPanel.Resources>
                <Style TargetType="TextBlock">
                    <Setter Property="Padding" Value="10"/>
                </Style>
            </StackPanel.Resources>
            <TextBlock>X:</TextBlock>
            <Slider Name="xSlider" Minimum="-200" Maximum="200" />
            <TextBlock>Y:</TextBlock>
            <Slider Name="ySlider" Minimum="-200" Maximum="200" />
        </StackPanel>
        <Image Source="baby-girl.jpg">
            <Image.RenderTransform>
                <TranslateTransform
                    X="{Binding ElementName=xSlider,Path=Value}"
                    Y="{Binding ElementName=ySlider,Path=Value}" />
            </Image.RenderTransform>
        </Image>
    </DockPanel>
</UserControl>

Minh họa:

WPF Translate Transfom

RotateTransform

<UserControl x:Class="TranformationsDemo.RotateTranformPanel"
             xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
             xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
             xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
             xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
             mc:Ignorable="d"
             d:DesignHeight="312" d:DesignWidth="372">
    <DockPanel LastChildFill="True">
        <StackPanel DockPanel.Dock="Left" Width="150" Margin="5">
            <StackPanel.Resources>
                <Style TargetType="TextBlock">
                    <Setter Property="Padding" Value="10"/>
                </Style>
            </StackPanel.Resources>
            <TextBlock>Angle (0° - 360°):</TextBlock>
            <Slider Name="angleSlider" Maximum="360" />
            <TextBlock>Center X:</TextBlock>
            <Slider Name="centerXSlider" Maximum="200"/>
            <TextBlock>Center Y:</TextBlock>
            <Slider Name="centerYSlider" Maximum="200" />
        </StackPanel>

        <Image Source="baby-girl.jpg">
            <Image.RenderTransform>
                <RotateTransform
                        Angle="{Binding ElementName=angleSlider,Path=Value}"
                        CenterX="{Binding ElementName=centerXSlider,Path=Value}"
                        CenterY="{Binding ElementName=centerYSlider,Path=Value}" />
            </Image.RenderTransform>
        </Image>

    </DockPanel>
</UserControl>

Minh họa:

WPF - Rotate Transform

ScaleTransform

<UserControl x:Class="TranformationsDemo.ScaleTranformPanel"
             xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
             xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
             xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
             xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
             mc:Ignorable="d"
             d:DesignHeight="323" d:DesignWidth="460">
    <DockPanel LastChildFill="True">
        <StackPanel DockPanel.Dock="Left" Width="150" Margin="5">
            <StackPanel.Resources>
                <Style TargetType="TextBlock">
                    <Setter Property="Padding" Value="10"/>
                </Style>
            </StackPanel.Resources>
            <TextBlock>Scale X (-300% - 300%):</TextBlock>
            <Slider Name="scaleXSlider" Minimum="-3" Maximum="3" Value="1" Ticks="0.1"/>
            <TextBlock>Scale Y (-300% - 300%):</TextBlock>
            <Slider Name="scaleYSlider" Minimum="-3" Maximum="3" Value="1" Ticks="0.1"/>
            <TextBlock>Center X:</TextBlock>
            <Slider Name="centerXSlider" Maximum="200"/>
            <TextBlock>Center Y:</TextBlock>
            <Slider Name="centerYSlider" Maximum="200" />
        </StackPanel>

        <Image Source="baby-girl.jpg">
            <Image.RenderTransform>
                <ScaleTransform
                        ScaleX="{Binding ElementName=scaleXSlider,Path=Value}"
                        ScaleY="{Binding ElementName=scaleYSlider,Path=Value}"
                        CenterX="{Binding ElementName=centerXSlider,Path=Value}"
                        CenterY="{Binding ElementName=centerYSlider,Path=Value}" />
            </Image.RenderTransform>
        </Image>

    </DockPanel>
</UserControl>

Minh họa:

WPF - Scale Transform

SkewTransform

<UserControl x:Class="TranformationsDemo.SkewTranformPanel"
             xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
             xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
             xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
             xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
             mc:Ignorable="d"
             d:DesignHeight="302" d:DesignWidth="414">
    <DockPanel LastChildFill="True">
        <StackPanel DockPanel.Dock="Left" Width="150" Margin="5">
            <StackPanel.Resources>
                <Style TargetType="TextBlock">
                    <Setter Property="Padding" Value="10"/>
                </Style>
            </StackPanel.Resources>
            <TextBlock>Angle X (-90° - 90°):</TextBlock>
            <Slider Name="angleXSlider" Minimum="-90" Maximum="90" />
            <TextBlock>Angle Y (-90° - 90°):</TextBlock>
            <Slider Name="angleYSlider" Minimum="-90" Maximum="90" />
            <TextBlock>Center X:</TextBlock>
            <Slider Name="centerXSlider" Maximum="200"/>
            <TextBlock>Center Y:</TextBlock>
            <Slider Name="centerYSlider" Maximum="200" />
        </StackPanel>

        <Image Source="baby-girl.jpg">
            <Image.RenderTransform>
                <SkewTransform
                        AngleX="{Binding ElementName=angleXSlider,Path=Value}"
                        AngleY="{Binding ElementName=angleYSlider,Path=Value}"
                        CenterX="{Binding ElementName=centerXSlider,Path=Value}"
                        CenterY="{Binding ElementName=centerYSlider,Path=Value}" />
            </Image.RenderTransform>
        </Image>
    </DockPanel>
</UserControl>

Minh họa:

WPF - Skew Transform

Kết hợp các Transform với TransformGroup

Sẽ có nhiều trường hợp bạn cần tạo một hiệu ứng từ nhiều kiểu Transform. Bởi vì property RenderTransform không cho phép chứa nhiều đối tượng, ta cần tạo một đối tượng chứa nhiều Transform và gán cho property này.

Như hình minh họa ở đầu bài bạn cũng thấy, lớp mà ta cần sử dụng là TransformGroup. Lớp này cũng được kế thừa từ Transform và chứa một property chính là Children có kiểu TransformCollection dùng để chứa nhiều Transform. Cách sử dụng lớp này rất đơn giản, bạn chỉ cần thêm các Transform cần dùng vào property Children và gán cho RenderTransform.

<Button Width="150" Height="50" Content="This is a Button" Name="button1">
    <Button.RenderTransform>
        <TransformGroup>

            <!-- Triple the size (scale) of the button in the Y direction. -->
            <ScaleTransform ScaleY="3" />

            <!-- Rotate the button by 45 degrees. -->
            <RotateTransform Angle="45" />
        </TransformGroup>
    </Button.RenderTransform>
</Button>

Kết hợp tất cả lại

MainWindow.xaml:

<Window x:Class="TranformationsDemo.MainWindow"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:local="clr-namespace:TranformingDemo"
        Title="Transformations Demo" Height="400" Width="550">
    <Grid>
        <TabControl>
            <TabItem Header="Translate Transform">
                <local:TranslateTransformPanel/>
            </TabItem>
            <TabItem Header="Rotate Transform">
                <local:RotateTranformPanel/>
            </TabItem>
            <TabItem Header="Scale Tranform">
                <local:ScaleTranformPanel/>
            </TabItem>
            <TabItem Header="Skew Transform">
                <local:SkewTranformPanel/>
            </TabItem>
        </TabControl>

    </Grid>
</Window>

App.xaml:

<Application x:Class="TranformationsDemo.App"
             xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
             xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
             StartupUri="MainWindow.xaml">
    <Application.Resources>
        <Style TargetType="Image">
            <Setter Property="Width" Value="200"/>
            <Setter Property="Height" Value="200" />
            <Setter Property="Stretch" Value="Fill"/>
            <Setter Property="Effect">
                <Setter.Value>
                    <DropShadowEffect Color="Black" Direction="-50" ShadowDepth="10" Opacity="0.5"/>
                </Setter.Value>
            </Setter>
        </Style>
    </Application.Resources>
</Application>

http://yinyangit.wordpress.com

 Chia sẻ qua: 
Hot!
Ý kiến bạn đọc

These items will be permanently deleted and cannot be recovered. Are you sure?

Gallery

image

Maecenas viverra rutrum pulvinar

Maecenas viverra rutrum pulvinar! Aenean vehicula nulla sit amet metus aliquam et malesuada risus aliquet. Vestibulum rhoncus, dolor sit amet venenatis porta, metus purus sagittis nisl, sodales volutpat elit lorem…

Read more

Text Links

Thiết kế logo chuyên nghiệp Insky
DAFABET
W88 w88b.com/dang-ky-tai-khoan-w88
W88
Copyright © 2011 - 2012 vietshare.vn by phamkhuong102@gmail.com doanhkisi2315@gmail.com. All rights reserved.