无法从父视图模型 WPF MVVM 应用程序中的弹出窗口获取值



我正在尝试从父视图模型访问子窗口视图模型的属性值。我正在从父视图模型调用窗口。我想根据子视图模型中的操作在主窗口中进行更改。我无法在父视图模型中获取子视图模型的任何值。我正在 MVVM 模式中尝试这个。

对话框界面

public interface IWindowService
{
void OpenDialogWindow(DialogViewModel vm);

}

父视图模型

public class FunctionalViewModel : INotifyPropertyChanged
{
private readonly IWindowService _windowService;
private string connectionString;
public string ConnectionString
{
get { return connectionString; }
set
{
connectionString = value;
PropertyChanged?.Invoke(this, new PropertyChangedEventArgs("ConnectionString"));
}
}
public FunctionalViewModel(IWindowService windowService)
{
BuildConnectionCommand = new RelayCommand(new Action<object>(BuildConnectionString));
_windowService = windowService;
}
private void BuildConnectionString(object obj)
{
MessageBox.Show("will open a window");
_windowService.OpenDialogWindow(new DialogViewModel());                                  
}
}

子视图模型

public class DialogViewModel : FunctionalViewModel,INotifyPropertyChanged
{
private string textboxsaf;
public string Textboxsaf
{
get { return textboxsaf; }
set {
textboxsaf = value;
PropertyChanged?.Invoke(this, new PropertyChangedEventArgs("Textboxsaf"));
}
}
private ICommand connectionCommand;
public ICommand ConnectionCommand
{
get { return connectionCommand; }
set { connectionCommand = value; }
}
public DialogViewModel()
{

ConnectionCommand = new RelayCommand(new Action<object>(SetValue));

}
public event PropertyChangedEventHandler PropertyChanged;

public void SetValue(object test)
{
textboxsaf= "ValueFromPopUpWindo";           
Application.Current.Windows[1].Close();

}

}

ChildWindow.xaml

<Grid>
<Label x:Name="label" Content="my popup window" HorizontalAlignment="Left" Margin="73,68,0,0" VerticalAlignment="Top" Width="132"/>
<TextBox x:Name="textBox" HorizontalAlignment="Left" Height="23" Margin="73,121,0,0" 
TextWrapping="Wrap" 
Text="{Binding Path=Textboxsaf,Mode=TwoWay}" VerticalAlignment="Top" Width="120"/>
<Button x:Name="button" Content="Button" HorizontalAlignment="Left"
Margin="109,177,0,0" VerticalAlignment="Top" Width="75"
Command="{Binding Path=ConnectionCommand }"
/>
</Grid>
</Window>

MainWindow.xaml

<Grid>
<Button Name="btnConnectionString" Grid.Row="0" Grid.Column="2" Content="Connection string" Height="40" Width="150"
Command="{Binding Path=BuildConnectionCommand}"
DataContext="{Binding tfs}"></Button>
</Grid>

主窗口文件的代码隐藏 MainWindow.xaml.cs

public partial class MainWindow : Window
{
public MainWindow()
{
InitializeComponent();
DataContext = new MainViewModel()
{
rel = new ReleaseViewModel(),
tfs =  new FunctionalViewModel(new WindowService()),
wnd = new DialogViewModel()
};
}

}
public class WindowService : IWindowService
{
public void OpenDialogWindow(DialogViewModel vm)
{
ConnectionWindow win = new ConnectionWindow();
win.DataContext = vm;            
win.Show();            
}               
}

问题

我想从父视图模型(功能视图模型(访问子视图模型(对话视图模型(中属性文本框saf的值。将Textboxsaf的值从 funcitonalviewModel 分配给ConnectionString。关闭窗口后很好。

我不会在PropertyChanged来检索DialogViewModel.Textboxsaf的值,因为这个属性在对话框的生命周期内可能会多次更改。

我会IWindowService.OpenDialogWindow返回自定义DialogResult对象或原始DialogViewModel可能会将IWindowService.OpenDialogWindow转换为异步方法。

或者,实现IWindowService.DialogClosed事件:

功能视图模型.cs

public class FunctionalViewModel : INotifyPropertyChanged
{
private readonly IWindowService _windowService;
private string connectionString;
public string ConnectionString
{
get { return connectionString; }
set
{
connectionString = value;
PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(nameof(this.ConnectionString)));
}
}
private void BuildConnectionString(object obj)
{
MessageBox.Show("will open a window");
_windowService.DialogClosed += OnDialogClosed;
_windowService.OpenDialogWindow(new DialogViewModel());                                  
}
private void OnDialogClosed(object sender,  DialogResultEventArgs e)
{
_windowService.DialogClosed -= OnDialogClosed;
ConnectionString = e.Result.Textboxsaf;
}
}

窗口服务.cs

public class WindowService : IWindowService
{
public event EventHandler<DialogResultEventArgs> DialogClosed;
public void OpenDialogWindow(DialogViewModel vm)
{
ConnectionWindow win = new ConnectionWindow();
win.DataContext = vm;
win.Closed += OnConnectionWindowClosed;
win.Show();            
} 

protected virtual void OnConnectionWindowClosed(object sender, EventArgs e)
{
var dialog = sender as FrameworkElement;
this.DialogClosed?.Invoke(this, new DialogResultEventArgs(dialog.DataContext as DialogViewModel));
}               
}

DialogResultEventArgs.cs

public class DialogResultEventArgs : EventArgs
{
public DialogViewModel Result { get; }

public DialogResultEventArgs(DialogViewModel result) => this.Result = result;
}

您可以保留对DialogViewModel的引用并订阅其PropertyChanged事件:

private void BuildConnectionString(object obj)
{
var childViewModel = new DialogViewModel();
childViewModel.PropertyChanged += OnChildPropertyChanged;
MessageBox.Show("will open a window");
_windowService.OpenDialogWindow(childViewModel);
}
private void OnChildPropertyChanged(object sender, PropertyChangedEventArgs e)
{
if (e.PropertyName == nameof(DialogViewModel.Textboxsaf))
{
childViewModel.PropertyChanged -= OnChildPropertyChanged;
ConnectionString = (sender as DialogViewModel)?.DialogViewModel;
}
}

相关内容

  • 没有找到相关文章

最新更新