Przechwycenie danych z pisaka

Architektura System.Windows.Input.StylusPlugIns zapewnia mechanizm implementowania kontroli niskiego poziomu nad Stylus danymi wejściowymi i tworzenia cyfrowych obiektów pisma odwrotowego Stroke . Klasa StylusPlugIn udostępnia mechanizm implementowania zachowania niestandardowego i stosowania go do strumienia danych pochodzących z urządzenia rysika w celu uzyskania optymalnej wydajności.

Ten temat zawiera następujące podsekcje:

Architektura

Jest to StylusPlugIn ewolucja interfejsów API StylusInput opisanych w artykule Uzyskiwanie dostępu do danych wejściowych pióra i manipulowanie nimi.

Każda z nich UIElement ma StylusPlugIns właściwość , która jest .StylusPlugInCollection Możesz dodać element StylusPlugIn do właściwości elementu StylusPlugIns , aby manipulować StylusPoint danymi podczas ich generowania. StylusPoint dane składają się ze wszystkich właściwości obsługiwanych przez system digitizer, w tym X danych i Y punktów, a także PressureFactor danych.

Obiekty StylusPlugIn są wstawiane bezpośrednio do strumienia danych pochodzących z Stylus urządzenia podczas dodawania StylusPlugInStylusPlugIns obiektu do właściwości . Kolejność dodawania wtyczek do StylusPlugIns kolekcji określa kolejność odbierania StylusPoint danych. Jeśli na przykład dodasz wtyczkę filtru, która ogranicza dane wejściowe do określonego regionu, a następnie dodaj wtyczkę, która rozpoznaje gesty podczas ich zapisywania, wtyczka, która rozpoznaje gesty odbiera odfiltrowane StylusPoint dane.

Implementowanie wtyczek rysików

Aby zaimplementować wtyczkę, należy utworzyć klasę z klasy StylusPlugIn. Ta klasa jest stosowana o strumień danych, który pochodzi z klasy Stylus. W tej klasie można modyfikować wartości StylusPoint danych.

Uwaga

Jeśli zgłasza StylusPlugIn lub powoduje wyjątek, aplikacja zostanie zamknięta. Należy dokładnie przetestować kontrolki korzystające z kontrolki StylusPlugIn i używać tylko wtedy, gdy masz pewność StylusPlugIn , że nie zgłosi wyjątku.

W poniższym przykładzie pokazano wtyczkę, która ogranicza dane wejściowe rysika, modyfikując X wartości i Y w StylusPoint danych, które pochodzą z Stylus urządzenia.

using System;
using System.Windows.Media;
using System.Windows;
using System.Windows.Input.StylusPlugIns;
using System.Windows.Input;
using System.Windows.Ink;
Imports System.Windows.Media
Imports System.Windows
Imports System.Windows.Input.StylusPlugIns
Imports System.Windows.Input
Imports System.Windows.Ink
// A StylusPlugin that restricts the input area.
class FilterPlugin : StylusPlugIn
{
    protected override void OnStylusDown(RawStylusInput rawStylusInput)
    {
        // Call the base class before modifying the data.
        base.OnStylusDown(rawStylusInput);

        // Restrict the stylus input.
        Filter(rawStylusInput);
    }

    protected override void OnStylusMove(RawStylusInput rawStylusInput)
    {
        // Call the base class before modifying the data.
        base.OnStylusMove(rawStylusInput);

        // Restrict the stylus input.
        Filter(rawStylusInput);
    }

    protected override void OnStylusUp(RawStylusInput rawStylusInput)
    {
        // Call the base class before modifying the data.
        base.OnStylusUp(rawStylusInput);

        // Restrict the stylus input
        Filter(rawStylusInput);
    }

    private void Filter(RawStylusInput rawStylusInput)
    {
        // Get the StylusPoints that have come in.
        StylusPointCollection stylusPoints = rawStylusInput.GetStylusPoints();

        // Modify the (X,Y) data to move the points
        // inside the acceptable input area, if necessary.
        for (int i = 0; i < stylusPoints.Count; i++)
        {
            StylusPoint sp = stylusPoints[i];
            if (sp.X < 50) sp.X = 50;
            if (sp.X > 250) sp.X = 250;
            if (sp.Y < 50) sp.Y = 50;
            if (sp.Y > 250) sp.Y = 250;
            stylusPoints[i] = sp;
        }

        // Copy the modified StylusPoints back to the RawStylusInput.
        rawStylusInput.SetStylusPoints(stylusPoints);
    }
}
' A StylusPlugin that restricts the input area.
Class FilterPlugin
    Inherits StylusPlugIn

    Protected Overrides Sub OnStylusDown(ByVal rawStylusInput As RawStylusInput)
        ' Call the base class before modifying the data.
        MyBase.OnStylusDown(rawStylusInput)

        ' Restrict the stylus input.
        Filter(rawStylusInput)

    End Sub


    Protected Overrides Sub OnStylusMove(ByVal rawStylusInput As RawStylusInput)
        ' Call the base class before modifying the data.
        MyBase.OnStylusMove(rawStylusInput)

        ' Restrict the stylus input.
        Filter(rawStylusInput)

    End Sub


    Protected Overrides Sub OnStylusUp(ByVal rawStylusInput As RawStylusInput)
        ' Call the base class before modifying the data.
        MyBase.OnStylusUp(rawStylusInput)

        ' Restrict the stylus input
        Filter(rawStylusInput)

    End Sub


    Private Sub Filter(ByVal rawStylusInput As RawStylusInput)
        ' Get the StylusPoints that have come in.
        Dim stylusPoints As StylusPointCollection = rawStylusInput.GetStylusPoints()

        ' Modify the (X,Y) data to move the points 
        ' inside the acceptable input area, if necessary.
        Dim i As Integer
        For i = 0 To stylusPoints.Count - 1
            Dim sp As StylusPoint = stylusPoints(i)
            If sp.X < 50 Then
                sp.X = 50
            End If
            If sp.X > 250 Then
                sp.X = 250
            End If
            If sp.Y < 50 Then
                sp.Y = 50
            End If
            If sp.Y > 250 Then
                sp.Y = 250
            End If
            stylusPoints(i) = sp
        Next i

        ' Copy the modified StylusPoints back to the RawStylusInput.
        rawStylusInput.SetStylusPoints(stylusPoints)

    End Sub
End Class

Dodawanie wtyczki do aplikacji InkCanvas

Najprostszym sposobem użycia niestandardowej wtyczki jest zaimplementowanie klasy pochodzącej z klasy InkCanvas i dodania StylusPlugIns jej do właściwości .

W poniższym przykładzie pokazano niestandardowy filtrujący InkCanvas atrament.

public class FilterInkCanvas : InkCanvas
{
    FilterPlugin filter = new FilterPlugin();

    public FilterInkCanvas()
        : base()
    {
        this.StylusPlugIns.Add(filter);
    }
}

Jeśli dodasz element FilterInkCanvas do aplikacji i uruchomisz ją, zauważysz, że atrament nie jest ograniczony do regionu, dopóki użytkownik nie zakończy pociągnięcia. Jest to spowodowane tym, że właściwość InkCanvas ma DynamicRenderer właściwość , która jest elementem StylusPlugIn i jest już członkiem kolekcji StylusPlugIns . Niestandardowy element StylusPlugIn dodany do kolekcji odbiera dane po DynamicRenderer odebraniu StylusPlugInsStylusPoint danych. W związku z tym StylusPoint dane nie będą filtrowane do momentu, gdy użytkownik podniesie pióro, aby zakończyć pociągnięcie. Aby przefiltrować atrament w miarę ściągania go przez użytkownika, należy wstawić FilterPlugin przed elementem DynamicRenderer.

Poniższy kod w języku C# demonstruje niestandardowy InkCanvas filtrujący atrament podczas rysowania.

public class DynamicallyFilteredInkCanvas : InkCanvas
{
    FilterPlugin filter = new FilterPlugin();

    public DynamicallyFilteredInkCanvas()
        : base()
    {
        int dynamicRenderIndex =
            this.StylusPlugIns.IndexOf(this.DynamicRenderer);

        this.StylusPlugIns.Insert(dynamicRenderIndex, filter);
    }
}

Podsumowanie

Wyprowadzając własne StylusPlugIn klasy i wstawiając je do StylusPlugInCollection kolekcji, możesz znacznie poprawić zachowanie cyfrowego pisma oddyskowego. Masz dostęp do StylusPoint danych generowanych w miarę ich generowania Stylus , co daje możliwość dostosowania danych wejściowych. Ponieważ masz taki niski dostęp do StylusPoint danych, możesz zaimplementować zbieranie pisma oddyskowego i renderowanie z optymalną wydajnością aplikacji.

Zobacz też