Pregunta

I am using Phone7.Fx R1

The following works. The system does not react when a user presses the button. This means, than there is no reaction if Stop Game is pressed without a game has been started and vice versa.

However the button looks active. I am aware that I can bind the IsEnabled to a different property, but I would like it to bind to NewGameCanExecute and StopGameCanExecute. Is this possible?

Some XAML code:

<Preview:BindableApplicationBarIconButton Command="{Binding NewGame}" IconUri="/images/icons/appbar.add.rest.png" Text="New game" />
        <Preview:BindableApplicationBarIconButton Command="{Binding StopGame}" IconUri="/images/icons/appbar.stop.rest.png" Text="Stop game" />

And the relay commands:

public RelayCommand NewGame { get; private set; }
public RelayCommand StopGame { get; private set; }

//Constructor
NewGame = new RelayCommand(NewGameExecute, NewGameCanExecute);
StopGame = new RelayCommand(StopGameExecute, StopGameCanExecute);

void NewGameExecute()
{
    _gameStarted = true;
    _gameControlModel.StartNewGame();
    StopGame.RaiseCanExecuteChanged();
}

bool NewGameCanExecute()
{
    return !_gameStarted;
}

void StopGameExecute()
{      
    _gameControlModel.StopGame();
    _gameStarted = false;
    NewGame.RaiseCanExecuteChanged();
}

bool StopGameCanExecute()
{
    return _gameStarted;
}

Couple of questions and answers:

Q: Have you tried to set a breakpoint in the CanExecute functions to see if it gets called?

A: Yes. It does get called, but the icon is not grayed out, eventhough false is returned. The Execute method is not executed, if the CanExecute method returns false. But I want the icon to be grayed out like a normal button.

SOLUTION

I spend some time and came up with a solution, which can be found here: http://pastebin.com/MM75xACj

¿Fue útil?

Solución 2

SOLUTION

I spend some time and came up with a solution and edited the applicationbariconbutton class.

namespace Phone7.Fx.Controls
{
    public class BindableApplicationBarIconButton : FrameworkElement, IApplicationBarIconButton
    {
        public int Index { get; set; }

        public static DependencyProperty CommandProperty = DependencyProperty.RegisterAttached("Command", typeof(ICommand), typeof(BindableApplicationBarIconButton), new PropertyMetadata(null, OnCommandPropertyChanged));
        private static void OnCommandPropertyChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
        {
            if (e.NewValue != e.OldValue)
            {
                ((BindableApplicationBarIconButton)d).Command = (ICommand)e.NewValue;
            }
        }

        public ICommand Command
        {
            get { return (ICommand)GetValue(CommandProperty); }
            set {
                    Command.CanExecuteChanged -= ValueOnCanExecuteChanged;
                SetValue(CommandProperty, value);
                Command.CanExecuteChanged += ValueOnCanExecuteChanged;
            }
        }

        private void ValueOnCanExecuteChanged(object sender, EventArgs eventArgs)
        {
            ICommand commandSender = sender as ICommand;
            if(commandSender != null)
            {IsEnabled = commandSender.CanExecute(null);}
        }

        public static readonly DependencyProperty CommandParameterProperty =
            DependencyProperty.RegisterAttached("CommandParameter", typeof(object), typeof(BindableApplicationBarIconButton), new PropertyMetadata(null, OnCommandParameterPropertyChanged));
        private static void OnCommandParameterPropertyChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
        {
            var invokeCommand = d as BindableApplicationBarIconButton;
            if (invokeCommand != null)
            {
                invokeCommand.SetValue(CommandParameterProperty, e.NewValue);
            }
        }
        public object CommandParameter
        {
            get { return GetValue(CommandParameterProperty); }
            set
            {
                SetValue(CommandParameterProperty, value);
            }
        }


        public static readonly DependencyProperty CommandParameterValueProperty =
          DependencyProperty.RegisterAttached("CommandParameterValue", typeof(object), typeof(BindableApplicationBarIconButton), null);
        public object CommandParameterValue
        {
            get
            {
                var returnValue = GetValue(CommandParameterValueProperty);
                return returnValue;
            }
            set { SetValue(CommandParameterValueProperty, value); }
        }

        public static readonly DependencyProperty IsEnabledProperty =
            DependencyProperty.RegisterAttached("IsEnabled", typeof(bool), typeof(BindableApplicationBarIconButton), new PropertyMetadata(true, OnEnabledChanged));

        private static void OnEnabledChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
        {
            if (e.NewValue != e.OldValue)
            {
                ((BindableApplicationBarIconButton)d).Button.IsEnabled = (bool)e.NewValue;
            }
        }

        public static readonly DependencyProperty TextProperty =
            DependencyProperty.RegisterAttached("Text", typeof(string), typeof(BindableApplicationBarIconButton), new PropertyMetadata(OnTextChanged));

        public new static readonly DependencyProperty VisibilityProperty =
           DependencyProperty.RegisterAttached("Visibility", typeof(Visibility), typeof(BindableApplicationBarIconButton), new PropertyMetadata(OnVisibilityChanged));

        private static void OnVisibilityChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
        {
            if (e.NewValue != e.OldValue)
            {
                var button = ((BindableApplicationBarIconButton)d);
                BindableApplicationBar bar = button.Parent as BindableApplicationBar;

                bar.Invalidate();
            }
        }

        public new Visibility Visibility
        {
            get { return (Visibility)GetValue(VisibilityProperty); }
            set { SetValue(VisibilityProperty, value); }
        }

        private static void OnTextChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
        {
            if (e.NewValue != e.OldValue)
            {
                ((BindableApplicationBarIconButton)d).Button.Text = e.NewValue.ToString();
            }
        }

        public ApplicationBarIconButton Button { get; set; }

        public BindableApplicationBarIconButton()
        {
            Button = new ApplicationBarIconButton();
            Button.Text = "Text";
            Button.Click += ApplicationBarIconButtonClick;
        }

        void ApplicationBarIconButtonClick(object sender, EventArgs e)
        {
            if (Command != null && CommandParameter != null)
                Command.Execute(CommandParameter);
            else if (Command != null)
                Command.Execute(CommandParameterValue);
            if (Click != null)
                Click(this, e);
        }

        public bool IsEnabled
        {
            get { return (bool)GetValue(IsEnabledProperty); }
            set { SetValue(IsEnabledProperty, value); }
        }

        public string Text
        {
            get { return (string)GetValue(TextProperty); }
            set { SetValue(TextProperty, value); }
        }

        public event EventHandler Click;

        public Uri IconUri
        {
            get { return Button.IconUri; }
            set { Button.IconUri = value; }
        }
    }

Otros consejos

This is obviously a bug in whatever BindableApplicationBarIconButton implementation you're using.

Ask the author of it for help, or debug your 3rd party software yourself.

Licenciado bajo: CC-BY-SA con atribución
No afiliado a StackOverflow
scroll top