Frage

Ich reagiere Ereignisse auf Elemente zu einer WPF Mouseleftbuttondown Leinwand hinzugefügt. Das alles funktioniert gut, wenn darauf geklickt wird (das heißt, die Eventhandler feuert richtig), aber es erfordert zu viel Präzision aus dem Mauszeiger. Sie haben vollkommen auf der Oberseite des Kreises sein, damit es funktioniert. Ich brauche es ein wenig toleranter zu sein; vielleicht mindestens 1 oder 2 pixles nachsichtig. Die Elemente auf der Leinwand sind schöne, große Kreise (etwa die Größe von einem Viertel auf dem Bildschirm), so dass die Kreise selbst sind nicht zu klein, aber die stroke eines jeden 1, so ist es eine dünne Linie ist.

Sie können einen Screenshot sehen hier: http://twitpic.com/1f2ci/full

Die meisten Grafik-Anwendung sind das nicht wählerisch über die Maus sammeln, so möchte ich dem Anwender eine vertraute Erfahrung geben.

Wie kann ich es ein wenig mehr zu vergeben.

War es hilfreich?

Lösung

Sie können bis zu dem Mouseleftbuttondown-Ereignis Ihres Root-Layout-Objekt Haken statt, und prüfen Sie, welche Elemente in Reichweite eines Klicks ist dies zu tun:

List<UIElement> hits = System.Windows.Media.VisualTreeHelper.FindElementsInHostCoordinates(Point, yourLayoutRootElement) as List<UIElement>;  

http://msdn.microsoft.com/ en-us / library / cc838402 (VS.95) aspx

Für den Punkt Parameter können Sie den MouseEventArgs Parameter e verwenden, und rufen Sie seine GetPosition Methode wie folgt:

Point p = e.GetPosition(null)

Ich kann mich nicht erinnern, ob HitTest zu verwenden, anstatt der FindElementsInHostCoordinates. Probieren Sie beide.
http://msdn.microsoft.com/en-us/library/ms608752. aspx

Sie können 4-Punkt-Objekte aus der Mausposition schaffen einen gefälschten-Toleranzeffekt zu erstellen, und entweder FindElementsInHostCoordinates oder HitTest für alle 4 Punkte nennen.

Andere Tipps

Sie könnten versuchen wollen, den Kreis mit dem Transparent Farbe zu füllen den ganzen Kreis anklickbar zu machen ...

Wenn das fehlschlägt, können Sie auch Helfer Kreise an der gleichen Stelle wie die anderen Kreise zeichnen. Machen Sie den Kreis Vordergrundfarbe Transparent, und stellen Sie die Dicke der Bürste ein paar Pixel breiter für eine akzeptablere klickbare Region um den Kreis ..

Hope, das hilft!

Ich glaube, ich habe es getan (mit ihr mir helfen, um loszulegen) ...

Als erstes habe ich den Umzug Veranstaltung zog in die Leinwand Handhabung statt jeder Ellipse. Das ist gut und schlecht, von einem OOP Standpunkt. Zumindest wenn die Maus Ereignisbehandlung eine Verantwortung des HolePattern ist, es auf bis jedes Loch (die Ellipse, die die visuellen des Lochs ist), wird abstrahiert, so dass jeder Verbraucher meiner HolePattern automactically dieses functioanality bekommen. Doch indem sie sie an den Haupt-UI-Code zu bewegen, habe ich jetzt mit meinem Leinwand Maus-Event auf einem höheren Niveau zu tun habe. Aber das ist nicht alles entweder schlecht. Wir können diesen Teil tagelang diskutieren.

Der Punkt ist, ich habe einen Weg entwickelt, um eine „Fehlermarge“ zu schaffen, wenn sie mit einer Maus etwas auf einer Leinwand Kommissionierung, und dann liest das Loch, das die ausgewählte Ellipse gehört, und dann kann ich die HolePattern gelesen, dass das Loch gehört, und meine ganze UI (Listview, Textfelder, gridview fo Koordinaten) wird alle durch die vorhandene XAML aktualisiert Bindung und die Canvas ist mit einem Aufruf zu einem bestehenden Verfahren aktualisiert, um die Leinwand zu regenerieren.

Um ehrlich zu sein, kann ich nicht glaube, ich habe das alles herausgefunden (mit Ihrer Hilfe und anderen natürlich auch). Es ist so ein geiles Gefühl die Vision dieses, dies zu haben und sehen, es kommen zu sein.

Überprüfen Sie den Haupt-Code aus hier:

void canvas1_MouseLeftButtonDown(object sender, MouseButtonEventArgs e)
{
    int ClickMargin = 2;
    Point ClickedPoint = e.GetPosition(canvas1);
    Point p1 = new Point(ClickedPoint.X - ClickMargin, ClickedPoint.Y - ClickMargin);
    Point p2 = new Point(ClickedPoint.X - ClickMargin, ClickedPoint.Y + ClickMargin);
    Point p3 = new Point(ClickedPoint.X + ClickMargin, ClickedPoint.Y + ClickMargin);
    Point p4 = new Point(ClickedPoint.X + ClickMargin, ClickedPoint.Y - ClickMargin);
    var PointPickList = new Collection<Point>();
    PointPickList.Add(ClickedPoint);
    PointPickList.Add(p1);
    PointPickList.Add(p2);
    PointPickList.Add(p3);
    PointPickList.Add(p4);

    foreach (Point p in PointPickList)
    {
        HitTestResult SelectedCanvasItem = System.Windows.Media.VisualTreeHelper.HitTest(canvas1, p);
        if (SelectedCanvasItem.VisualHit.GetType() == typeof(Ellipse))
        {
            var SelectedEllipseTag = SelectedCanvasItem.VisualHit.GetValue(Ellipse.TagProperty);
            if (SelectedEllipseTag!=null &&  SelectedEllipseTag.GetType().BaseType == typeof(Hole))
            {
                Hole SelectedHole = (Hole)SelectedEllipseTag;
                SetActivePattern(SelectedHole.ParentPattern);
                SelectedHole.ParentPattern.CurrentHole = SelectedHole;

            }
        }
    }
}

Just Strichstärke der Ellipse erhöhen, so dass es einstellbar ist

damit die Veranstaltung Werke Mouseleftbuttondown Beispiel: In Ellipse-Tag:

Ellipse  Canvas.Left = "10" Canvas.Top = "133" height = "24" Name = "ellipse1" width = "23" Stroke = "Red" Mouseleftbuttondown = "ellipse1_MouseLeftButtonDown" Quick-Info = "Temp Close" StrokeEndLineCap = "Flat" StrokeThickness = "12"

private void ellipse1_MouseLeftButtonDown (object sender, MouseButtonEventArgs e)         {             Anwendung curApp = Application.Current;             curApp.Shutdown ();         }

Lizenziert unter: CC-BY-SA mit Zuschreibung
Nicht verbunden mit StackOverflow
scroll top