Kailayla
Kailayla

Reputation: 323

WPF - Window doesn't close

I used the following answer to get a new window and be able to use the values in another ViewModel: https://stackoverflow.com/a/15512972/3793542

I implemented this to my application, where a user can add a new Customer. To do this, he/she clicks the button in the CustomerDetailsView, and a new window opens (CustomerAddView). Then he/she fill out the details and clicks the button in the window.
Now, the Customer is added, my ListBox updates just fine. But the window doesn't close.
I was hoping that any of you can spot what's wrong, as I can't seem to be able to figure it out and it's been driving me crazy.

The code
The OpenCloseWindowBehavior as mentioned in the linked answer is the same, only renamed to WindowBehavior.

Here's the view where the button is, CustomerDetailsView (shortened a bit):

<UserControl x:Class="QRM.View.CustomerDetailsView"
             xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
             xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
             xmlns:i="http://schemas.microsoft.com/expression/2010/interactivity"
             xmlns:src="clr-namespace:QRM"
             xmlns:view="clr-namespace:QRM.View"
             xmlns:viewmodel="clr-namespace:QRM.ViewModel"
             xmlns:helpers="clr-namespace:QRM.Helpers">
    <UserControl.DataContext>
        <viewmodel:CustomerDetailsViewModel />
    </UserControl.DataContext>
    <UserControl.Resources>
        <ResourceDictionary Source="../StylesRD.xaml" />
    </UserControl.Resources>
    <i:Interaction.Behaviors>
        <!-- TwoWay binding is necessary, otherwise after user closed a window directly, it cannot be opened again -->
        <helpers:WindowBehavior WindowType="view:CustomerAddView" Open="{Binding AddCustomerOpen, Mode=TwoWay}" />
    </i:Interaction.Behaviors>

    <Grid Margin="5">
        <Grid.RowDefinitions>
            <RowDefinition Height="4*"/>
            <RowDefinition Height="auto"/>
            <RowDefinition Height="1*"/>
            <RowDefinition Height="auto"/>
            <RowDefinition Height="1*"/>
        </Grid.RowDefinitions>

        <Grid Margin="0,5,0,0">
            <!-- Grid with all the details-->
        </Grid>

        <Line Grid.Row="1" Style="{StaticResource horizontalLineStyle}" />

        <StackPanel Grid.Row="2" Orientation="Vertical">
            <Button Command="{Binding AddCommand}" CommandParameter="True"> Add a new customer</Button>
            <!-- More buttons-->
        </StackPanel>

        <Line Grid.Row="3" Style="{StaticResource horizontalLineStyle}" />

        <StackPanel Grid.Row="4" Orientation="Vertical">
            <!-- More buttons-->
        </StackPanel>    
    </Grid>        
</UserControl>

The new window CustomerAddView:

<Window x:Class="QRM.View.CustomerAddView"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:viewmodel="clr-namespace:QRM.ViewModel"
        Title="Add Customer" ResizeMode="NoResize" SizeToContent="WidthAndHeight" WindowStartupLocation="CenterScreen">
    <Window.DataContext>
        <viewmodel:CustomerAddViewModel />
    </Window.DataContext>
    <Window.Resources>
        <ResourceDictionary Source="../StylesRD.xaml" />
    </Window.Resources>

    <Grid Margin="5">
        <Grid.RowDefinitions>
            <RowDefinition/>
            <RowDefinition/>
            <RowDefinition/>
        </Grid.RowDefinitions>

        <Grid.ColumnDefinitions>
            <ColumnDefinition Width="auto" />
            <ColumnDefinition Width="auto" />
            <ColumnDefinition Width="200" />
        </Grid.ColumnDefinitions>

        <!-- Form to put in new Customer's details-->

        <Button Grid.Row="2" Grid.ColumnSpan="3" Margin="0,50,0,0"
                Command="{Binding AddConfirmCommand}">Add this customer</Button>
    </Grid>            
</Window>

CustomerDetailsViewModel:

public class CustomerDetailsViewModel : INotifyPropertyChanged
    {
        public bool isSelected = false;
        private Nullable<bool> isVisible = new Nullable<bool>();
        DBCustomer dbCustomer = new DBCustomer();

        #region Constructor
        public CustomerDetailsViewModel()
        {
            Messenger messenger = App.Messenger;
            messenger.Register("CustomerSelectionChanged", (Action<Customer>)(param => ProcessCustomer(param)));
        }
        #endregion

        #region Add a Customer
        private bool _addCustomerOpen;
        public bool AddCustomerOpen { get { return _addCustomerOpen; } set { _addCustomerOpen = value; OnPropertyChanged("AddCustomerOpen"); } }

        private RelayCommand addCommand;
        public ICommand AddCommand
        {
            get { return addCommand ?? (addCommand = new RelayCommand(() => AddCustomer())); }
        }

        private void AddCustomer()
        {
            this.AddCustomerOpen = true;
        }

        //After pressing the button in AddView
        private RelayCommand addDoneCommand;
        public ICommand AddDoneCommand
        {
            get { return addDoneCommand ?? (addDoneCommand = new RelayCommand(() => AddCustomerDone(), () => !isSelected)); }
        }

        public void AddCustomerDone()
        {
            App.Messenger.NotifyColleagues("NewCustomer");
            this.AddCustomerOpen = false;
        }
        #endregion

        #region PropertyChanged
        public event PropertyChangedEventHandler PropertyChanged;
        public void OnPropertyChanged(PropertyChangedEventArgs e)
        {
            if (PropertyChanged != null)
                PropertyChanged(this, e);
        }
        private void OnPropertyChanged(string propertyName)
        {
            if (this.PropertyChanged != null)
                PropertyChanged(this, new PropertyChangedEventArgs(propertyName));
        }
        #endregion
    }

CustomerAddViewModel:

class CustomerAddViewModel : INotifyPropertyChanged
    {
        private RelayCommand addConfirmCommand;
        DBCustomer dbCustomer = new DBCustomer();

        public ICommand AddConfirmCommand
        {
            get { return addConfirmCommand ?? (addConfirmCommand = new RelayCommand(() => AddConfirmCustomer())); }
        }

        private void AddConfirmCustomer()
        {
            if (!dbCustomer.Create(newCustomer))
            {
                return;
            }
            CustomerDetailsViewModel _closeTheWindow = new CustomerDetailsViewModel();
            _closeTheWindow.AddDoneCommand.Execute(false);
        }

        private Customer newCustomer = new Customer();
        public Customer NewCustomer
        {
            get { return newCustomer; }
            set { newCustomer = value; OnPropertyChanged(new PropertyChangedEventArgs("NewCustomer")); }
        }

        #region PropertyChanged
        public event PropertyChangedEventHandler PropertyChanged;
        public void OnPropertyChanged(PropertyChangedEventArgs e)
        {
            if (PropertyChanged != null)
                PropertyChanged(this, e);
        }
        #endregion
    }

Upvotes: 0

Views: 76

Answers (1)

Evk
Evk

Reputation: 101613

Well you create new instance of CustomerDetailsViewModel here:

CustomerDetailsViewModel _closeTheWindow = new CustomerDetailsViewModel();
_closeTheWindow.AddDoneCommand.Execute(false);

This instance is not related to anything and it's AddCustomerOpen property is not bound to anything either, so setting it has no effect.

Upvotes: 2

Related Questions