2016-07-04 9 views
0

テスト用のUWPフォームでは、以下の基本的な操作テストがあります。 CanvasControlに3つの円を描き、翻訳とスケーリングの操作を設定します。操作のデルタ - 奇妙な効果とオーバーフローへの対応

これをタッチスクリーンでテストすると、基本的に画面上の2本の指の位置に基づいて円を翻訳してズームします。しかし、特定のポイントを超えてピンチダウンした場合、画像は2エクステント間で非常に急速に振動し始め、非常に迅速にコードがオーバーフローで停止する原因となります。

キャンバスコントロールをグリッドに配置し、グリッドコントロールからキャンバスコントロールの操作を試みましたが、ズームやパンの効果は正しくないようですが、同じ問題が発生しません。

私のコードのように見えますが、反復です。レンダリングトランスフォームの変更を引き起こす操作が別の操作を引き起こす可能性があり、それが落ち着くまで、または精度が問題になるまでおそらくタッチポイント間の距離が小さすぎるために、反復はオーバーフローするまで発散する。

これは予想されますか?これを行う正しい方法は何ですか?

Private WithEvents Canv As New CanvasControl 
Private WithEvents gr As New Grid 


Private Sub Canv_Draw(sender As CanvasControl, args As CanvasDrawEventArgs) Handles Canv.Draw 
    args.DrawingSession.DrawCircle(50, 50, 25, Windows.UI.Colors.Blue) 
    args.DrawingSession.DrawCircle(250, 250, 25, Windows.UI.Colors.Blue) 
    args.DrawingSession.DrawCircle(500, 500, 25, Windows.UI.Colors.Blue) 
End Sub 

Public Sub New() 

    ' This call is required by the designer. 
    InitializeComponent() 

    ' Add any initialization after the InitializeComponent() call. 

    Content = gr 
    gr.Children.Add(Canv) 


    Canv.ManipulationMode = ManipulationModes.Scale Or ManipulationModes.TranslateX Or ManipulationModes.TranslateY 

end sub 


Private Sub Canv_ManipulationDelta(sender As Object, e As ManipulationDeltaRoutedEventArgs) Handles Canv.ManipulationDelta 
    Dim t As New TranslateTransform 

    t.X = e.Cumulative.Translation.X 
    t.Y = e.Cumulative.Translation.Y 


    Dim s As New ScaleTransform 
    s.ScaleX = e.Cumulative.Scale 
    s.ScaleY = e.Cumulative.Scale 
    s.CenterX = e.Position.X 
    s.CenterY = e.Position.Y 

    Dim g As New TransformGroup 
    g.Children.Add(s) 
    g.Children.Add(t) 

    Canv.RenderTransform = g 



End Sub 

答えて

0

UWPでの一般的な方法はCompositeTransformを使用することです、それはスケール、スキュー、回しをサポートしてを翻訳。

、ズームの問題については、特にthe forth scenario

をBasicInputサンプルを参照してください、あなたは以下の方法を使用してそれを避けることができますが:

Public NotInheritable Class MainPage 
Inherits Page 

Private WithEvents Canv As New CanvasControl 
Private WithEvents gr As New Grid 

Private Sub Canv_Draw(sender As CanvasControl, args As CanvasDrawEventArgs) Handles Canv.Draw 
    args.DrawingSession.DrawCircle(50, 50, 25, Windows.UI.Colors.Blue) 
    args.DrawingSession.DrawCircle(250, 250, 25, Windows.UI.Colors.Blue) 
    args.DrawingSession.DrawCircle(500, 500, 25, Windows.UI.Colors.Blue) 
End Sub 

Public Sub New() 

    ' This call is required by the designer. 
    InitializeComponent() 

    ' Add any initialization after the InitializeComponent() call. 

    Content = gr 
    gr.Children.Add(Canv) 

    Canv.ManipulationMode = ManipulationModes.Scale Or ManipulationModes.TranslateX Or ManipulationModes.TranslateY 

End Sub 

Private Sub Canv_ManipulationDelta(sender As Object, e As ManipulationDeltaRoutedEventArgs) Handles Canv.ManipulationDelta 
    Dim tran = Transform(sender) 
    tran.ScaleX = tran.ScaleX * e.Delta.Scale 
    tran.ScaleY = tran.ScaleY * e.Delta.Scale 
    'System.Diagnostics.Debug.WriteLine("tran.ScaleX =" + tran.ScaleX.ToString() + " tran.ScaleY =" + tran.ScaleY.ToString()) 
End Sub 

Private Function Transform(sender As Object) As CompositeTransform 
    Dim rect = TryCast(sender, CanvasControl) 
    rect.RenderTransformOrigin = New Point(0.5, 0.5) 
    Dim tran As New CompositeTransform 
    If TryCast(rect.RenderTransform, CompositeTransform) IsNot Nothing Then 
     tran = DirectCast(rect.RenderTransform, CompositeTransform) 
    Else 
     rect.RenderTransform = New CompositeTransform() 
    End If 
    Return tran 
End Function 

' utility method 
Private Function Boundary(value As Double, min As Double, max As Double) As Double 
    If value > max Then 
     Return max 
    ElseIf value < min Then 
     Return min 
    Else 
     Return value 
    End If 
End Function 
End Class 

スクリーンショット: Gif

0

いくつかの有用なその中で、その間、私はグリッドにCanvasControlを残して操作を取るというきちんとした解決策を見つけましたイベントをグリッドから取得し、キャンバスコントロールのレンダリングトランスフォームを変更すると、再帰はありません。また、自然な翻訳が正しくないことを意味しますが、これは累積的なスケールでそれを掛けて修正するのは簡単です。完全な操作コードは次のようになります。

Private Sub GerberCanvGrid_ManipulationDelta(sender As Object, e As ManipulationDeltaRoutedEventArgs) Handles GerberCanvGrid.ManipulationDelta 
    Dim sf As New ScaleTransform 
    sf.ScaleX = e.Cumulative.Scale 
    sf.ScaleY = e.Cumulative.Scale 
    sf.CenterX = e.Position.X 
    sf.CenterY = e.Position.Y 

    Dim tt As New TranslateTransform 
    tt.X = e.Cumulative.Translation.X * e.Cumulative.Scale 
    tt.Y = e.Cumulative.Translation.Y * e.Cumulative.Scale 

    ManipulationTransform = New TransformGroup 
    ManipulationTransform.Children.Add(sf) 
    ManipulationTransform.Children.Add(tt) 
    GerberCanv.RenderTransform = ManipulationTransform 
End Sub