0

いくつかの Ellipse オブジェクトを含む WPF キャンバスがあります (円として表示されます)。各円は、実際にはカスタム ホール パターン クラスであるコレクション クラス インスタンスからのものです。各パターンには特定の数の円があり、次のコードを使用してコレクションを反復処理することにより、各円がキャンバスに追加されます。

したがって、キャンバスには多数の円が取り込まれ、各円は特定のパターン インスタンスに属します。ここでスクリーンショットを見ることができます: http://twitpic.com/1f2ci/full

ここで、キャンバス上の円をクリックする機能を追加し、それが属するコレクションを判別できるようにして、その円が属する選択されたパターンでさらに作業を行えるようにします。

public void DrawHoles()
{
   // Iterate over each HolePattern in the HolePatterns collection... 
   foreach (HolePattern HolePattern in HolePatterns)
    {
        // Now iterate over each Hole in the HoleList of the current HolePattern...
        // This code adds the HoleEntity, HoleDecorator, and HoleLabel to the canvas
        foreach (Hole Hole in HolePattern.HoleList)
        {

            Hole.CanvasX = SketchX0 + (Hole.AbsX * _ZoomScale);
            Hole.CanvasY = SketchY0 - (Hole.AbsY * _ZoomScale);
            canvas1.Children.Add(Hole.HoleEntity);
        }
    }
}
4

3 に答える 3

3

すべてFrameworkElementsに、Tag任意の情報を保持するために使用できるオブジェクト型のプロパティがあります。HolePatternTagプロパティに割り当て、後で簡単に使用して関連するコレクションを取得できます。

すなわち:

...
Hole.HoleEntity.Tag = HolePattern as object;
canvas1.Children.Add(Hole.HoleEntity);

後でクリックイベントで:

event(object sender,....)
{
   Ellipse e = sender as Ellipse;
   HolePattern hp = e.Tag as HolePattern;
   ...
}
于 2009-02-23T22:33:29.153 に答える
0

他の人に役立つ場合に備えて、最終的でより洗練されたソリューションを投稿すると思いました。

void canvas1_MouseLeftButtonDown(object sender, MouseButtonEventArgs e)
{
    int ClickMargin = 2;// Adjust here as desired. Span is in both directions of selected point.
    var ClickMarginPointList = new Collection<Point>();
    Point ClickedPoint = e.GetPosition(canvas1);
    Point ClickMarginPoint=new Point();
    for (int x = -1 * ClickMargin; x <= ClickMargin; x++)
    {
        for (int y = -1 * ClickMargin; y <= ClickMargin; y++)
        {
            ClickMarginPoint.X = ClickedPoint.X + x;
            ClickMarginPoint.Y = ClickedPoint.Y + y;
            ClickMarginPointList.Add(ClickMarginPoint);
        }
    }

    foreach (Point p in ClickMarginPointList)
    {
        HitTestResult SelectedCanvasItem = System.Windows.Media.VisualTreeHelper.HitTest(canvas1, p);
        if (SelectedCanvasItem.VisualHit.GetType().BaseType == typeof(Shape))
        {
            var SelectedShapeTag = SelectedCanvasItem.VisualHit.GetValue(Shape.TagProperty);
            if (SelectedShapeTag!=null &&  SelectedShapeTag.GetType().BaseType == typeof(Hole))
            {
                Hole SelectedHole = (Hole)SelectedShapeTag;
                SetActivePattern(SelectedHole.ParentPattern);
                SelectedHole.ParentPattern.CurrentHole = SelectedHole;
                return; //Get out, we're done.
            }
        }
    }
}
于 2009-02-24T20:18:58.707 に答える
0

ですから、あなたはおそらく、私がそれが機能していると私が言った私の返信をすでに読んでいるでしょう。そして、それは完全に機能します (マウスで非常に高い精度を必要とすることを除いて) が、私はこれを尋ねたいです: キャンバスに追加されるすべての楕円にイベント ハンドラーを追加するのは本当に賢明ですか? 今、私はそれがどのような種類のメモリボグであるかを知りません.WPFとWindowsが処理するのは簡単なことかもしれません.

実際には、複数のパターンが表示された画面でも 30 ~ 50 個の穴しかないと思いますが、それでも、 50 個のイベント ハンドラー? ただ怖いようです。実際、各「穴」は 2 つの同心円とテキスト ラベルで視覚的に表現されており (こちらのスクリーン ショーを参照してください: http://twitpic.com/1f2ci/full )、ユーザーがクリックできることを期待していることはわかっています。これらの要素のいずれかを選択して穴を選択します。つまり、穴ごとに 3 つの要素のイベント ハンドラーを意味します。これで、100 以上のイベント ハンドラーについて話している可能性があります。

Canvas にイベント ハンドラを 1 つだけ配置し、マウスの下で要素参照を読み取り、それから作業してその要素の .Tag プロパティを取得するなどの解決策が必要なようです。

于 2009-02-24T06:11:41.457 に答える