WP7: Подавление сенсорного ввода XNA при обработке Silverlight? - PullRequest
5 голосов
/ 28 июля 2011

У меня есть игра XNA + Silverlight в Mango: в основном XNA с некоторым пользовательским интерфейсом Silverlight сверху.У меня проблема в том, что когда вы нажимаете кнопку или взаимодействуете с элементом управления Silverlight, сенсорная информация все еще передается в игровой цикл XNA.Как вы это подавляете?

Ответы [ 2 ]

4 голосов
/ 29 июля 2011

Написал класс, чтобы сделать отслеживание для меня. После загрузки страницы (в обработчике Loaded) создайте его и присвойте ему корневой элемент (чтобы он мог присоединиться к событию LayoutUpdated). Зарегистрируйте любые элементы управления, которые могут перекрывать поверхность игры во время игры Затем просто вызовите TouchesControl и перейдите в позицию касания, чтобы узнать, следует ли вам игнорировать эту точку или нет. Он кэширует области элементов управления и обновляет их при обновлении макета.

Должно работать для перемещения прямоугольных элементов, изменения размера или сжатия / расширения.

public class ControlTouchTracker
{
    private List<FrameworkElement> controls = new List<FrameworkElement>();
    private Dictionary<FrameworkElement, ControlRegion> controlBounds = new Dictionary<FrameworkElement, ControlRegion>();

    public ControlTouchTracker(FrameworkElement rootElement)
    {
        rootElement.LayoutUpdated += this.OnLayoutUpdated;
    }

    public void RegisterControl(FrameworkElement control)
    {
        controls.Add(control);
    }

    public void RemoveControl(FrameworkElement control)
    {
        controls.Remove(control);
        controlBounds.Remove(control);
    }

    private void OnLayoutUpdated(object sender, EventArgs e)
    {
        foreach (Control control in this.controls)
        {
            this.RefreshControlBounds(control);
        }
    }

    private void RefreshControlBounds(FrameworkElement control)
    {
        if (this.ControlIsVisible(control))
        {
            try
            {
                GeneralTransform controlTransform = control.TransformToVisual(Application.Current.RootVisual);
                Point offset = controlTransform.Transform(new Point(0, 0));

                this.controlBounds[control] = new ControlRegion
                {
                    Left = (float)offset.X,
                    Right = (float)(offset.X + control.ActualWidth),
                    Top = (float)offset.Y,
                    Bottom = (float)(offset.Y + control.ActualHeight)
                };
            }
            catch (ArgumentException)
            {
            }
        }
        else
        {
            if (this.controlBounds.ContainsKey(control))
            {
                this.controlBounds.Remove(control);
            }
        }
    }

    private bool ControlIsVisible(FrameworkElement control)
    {
        // End case
        if (control == null)
        {
            return true;
        }

        if (control.Visibility == Visibility.Collapsed)
        {
            return false;
        }

        return this.ControlIsVisible(control.Parent as FrameworkElement);
    }

    public bool TouchesControl(Vector2 touchPosition)
    {
        foreach (ControlRegion region in this.controlBounds.Values)
        {
            if (touchPosition.X >= region.Left && touchPosition.X <= region.Right &&
                touchPosition.Y >= region.Top && touchPosition.Y <= region.Bottom)
            {
                return true;
            }
        }

        return false;
    }

    public class ControlRegion
    {
        public float Left { get; set; }
        public float Right { get; set; }
        public float Top { get; set; }
        public float Bottom { get; set; }
    }
}

(правка) Обновлен пример работы с изменением родительских элементов Visibility.

3 голосов
/ 28 июля 2011

Благодаря тому, как работает взаимодействие с XNA, вы всегда будете обрабатывать сенсорный ввод как XNA, так и Silverlight - в некоторой степени XNA получает приоритет, поэтому Silverlight действует поверх этого.Что вы можете сделать, если вам нужно игнорировать определенные местоположения жестов (например, где расположены кнопки Silverlight), вы можете проверить положение жестов:

if (TouchPanel.IsGestureAvailable)
{
    if (TouchPanel.ReadGesture().GestureType == GestureType.Tap)
    {
        if (TouchPanel.ReadGesture().Position == new Vector2(120, 120))
        {

        }
    }
}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...