テストのテスト
グループ化後の回転
これを真似したい
同じ色どうしがグループ化されていると見倣して、グループを回転させた時の動作
水色のThumbの回転軸は自身の中心
桃色のThumbの回転軸も自身の中心だけど、回転軸のセットを押すと2つのThumbの中央に切り替わる、エクセルと同じなのはこちら
Imports System.Windows.Controls.Primitives
Class MainWindow
Private g1 As New List(Of Thumb)
Private g2 As New List(Of exThumb)
Private Function GetCenterPoint(t As Thumb) As Point
Dim gt As GeneralTransform = t.TransformToVisual(canvas1)
Dim cp As New Point(t.Width / 2, t.Height / 2)
Dim np As Point = gt.Transform(cp)
Return np
End Function
Private Sub SetLocate(t As Thumb, p As Point)
Canvas.SetLeft(t, p.X)
Canvas.SetTop(t, p.Y)
End Sub
Private Function GetTransformGroup() As TransformGroup
Dim tg As New TransformGroup
With tg.Children
.Add(New ScaleTransform(1, 1))
.Add(New SkewTransform)
.Add(New RotateTransform(0))
.Add(New TranslateTransform)
End With
Return tg
End Function
Private Function AddThumb(p As Point) As Thumb
Dim t As New Thumb
With t
.Width = 50
.Height = 50
.Background = Brushes.Cyan
.RenderTransform = GetTransformGroup()
.RenderTransformOrigin = New Point(0.5, 0.5)
End With
Call SetLocate(t, p)
canvas1.Children.Add(t)
Return t
End Function
Private Function AddexThumb(p As Point) As exThumb
Dim t As New exThumb
With t
.Width = 50
.Height = 50
.Background = Brushes.Pink
.RenderTransform = GetTransformGroup()
.RenderTransformOrigin = New Point(0.5, 0.5)
End With
Call SetLocate(t, p)
canvas1.Children.Add(t)
Return t
End Function
Private Function GetRect(t As exThumb) As Rect
Dim gt As GeneralTransform = t.TransformToVisual(canvas1)
Dim r As Rect = gt.TransformBounds(New Rect(New Size(t.Width, t.Height)))
Return r
End Function
Private Function GetGroupRect(rl As List(Of Rect)) As Rect
Dim minX As Double = rl(0).X
Dim minY As Double = rl(0).Y
Dim maxX As Double = minX + rl(0).Width
Dim maxY As Double = minY + rl(0).Height
Dim r As Rect
For i As Integer = 1 To rl.Count - 1
r = rl(i)
minX = Math.Min(minX, r.X)
minY = Math.Min(minY, r.Y)
maxX = Math.Max(maxX, r.X + r.Width)
maxY = Math.Max(maxY, r.Y + r.Height)
Next
r = New Rect(minX, minY, maxX - minX, maxY - minY)
Return r
End Function
Private Sub haiti()
g1.Add(AddThumb(New Point(50, 100)))
g1.Add(AddThumb(New Point(150, 100)))
g2.Add(AddexThumb(New Point(300, 100)))
g2.Add(AddexThumb(New Point(400, 100)))
End Sub
Private Sub MainWindow_ContentRendered(sender As Object, e As EventArgs) Handles Me.ContentRendered
Call haiti()
End Sub
Private Sub bt1_Click(sender As Object, e As RoutedEventArgs) Handles bt1.Click
For Each t As Thumb In g1
Dim ro As New RotateTransform(15)
Dim tg As TransformGroup = t.RenderTransform
tg.Children.Add(ro)
Next
End Sub
Private Sub bt2_Click(sender As Object, e As RoutedEventArgs) Handles bt2.Click
For Each t As exThumb In g2
Dim ro As New RotateTransform(15, t.TransformAxis.X, t.TransformAxis.Y)
Dim tg As TransformGroup = t.RenderTransform
tg.Children.Add(ro)
Next
End Sub
Private Sub bt3_Click(sender As Object, e As RoutedEventArgs) Handles bt3.Click
Dim rl As New List(Of Rect)
For Each t As exThumb In g2
t.CenterPoint = GetCenterPoint(t)
rl.Add(GetRect(t))
Next
Dim r As Rect = GetGroupRect(rl)
Dim x As Double = r.Width / 2 + r.Left
Dim y As Double = r.Height / 2 + r.Top
Dim cp As New Point(x, y)
For Each t As exThumb In g2
t.GroupCenterPoint = cp
Dim np As Point = t.GroupCenterPoint - t.CenterPoint
t.TransformAxis = np
Next
End Sub
Private Sub bt4_Click(sender As Object, e As RoutedEventArgs) Handles bt4.Click
g1.Clear()
g2.Clear()
canvas1.Children.RemoveRange(0, 4)
haiti()
End Sub
End Class
Public Class exThumb
Inherits Thumb
Public Property CenterPoint As Point
Public Property GroupCenterPoint As Point
Public Property TransformAxis As Point
End Class
WPFでのコン
トロールの描画位置、レイアウトはRenderTransformを指定する
回転や拡大率などの変形もRenderTransformにそれぞれのTransformを指定する
拡大して回転とかの複数の変形をする場合はTransformのCollectionを作って
TransformGroupのChildrenに追加する感じになる
Dim tg As New TransformGroup
tg.Children.Add(New ScaleTransform(2,2)) '縦横2倍に拡大
tg.Children.Add(New RotateTransform(15)) '15度回転
Thumb.RenderTransform = tg
回転軸は特に指定しないと左上が軸になるので自身の中心を軸にする場合は
コン
トロールのRenderTransformOriginプロパティに Point(0.5,0.5)を指定する
Thumb.RenderTransformOrigin = New Point(0.5,0.5)
これが基本になって
ここからさらに回転させるときは
A:自身のRenderTransformの中からRotateTransformを探しだして、その中のAngleプロパティを変更する
B:新たにRotateTransformを作って自身のRenderTransformのGroupに追加する
このどちらかになると思う
Aはムダがないけどちょっとめんどくさい
Bはラクだけど回転の変更する度に追加するからかなりのムダ、きりがない
きりがないけど今回は回転軸の変更が目的だから妥協してこちらを採用
回転軸用のプロパティを持ったThumb
グループ化後は回転軸を変更するので、その軸の位置をThumb自身に持たせるためにThumbを継承したexThumbって名前をつけたClassを作成
軸の位置はTransformAxisって名前をつけた
その他のCenterPointとGroupCenterPointは確認用
自身の中心点を取得するのにTransformToVisualを使っているけど
Canvas.GetLeftと
Canvas.GetTopを使って左上の位置を取得してから、自身のサイズから計算するのもあるなあ
グループ化後の回転軸の位置
グループのサイズの中心位置 - グループ化前の自身の中心点位置(133行目)
これがグループ化後の回転軸の位置TransformAxisになる(134行目)
グループ化後の回転
TransformAxisを使って回転軸を指定したRotateTransformを作成(112行目)
RenderTransformにRotateTransformを追加
今回の方法ではきりがない
回転に5回変更を加えてから一時停止してRenderTransformの中を見てみると
RotateTransformが5個ズラーっと並んでいるのがわかる
次回はこれを直すのとグループ化を解除するときの動作のテスト