作为WPF和MVVM的初学者,我有两个问题: 我构建了一个用户控件,它在一个窗口中使用,并包含两个StackPanel。
提前谢谢
编辑按钮(列)
<GridViewColumn Header="Edit" Width="auto">
<GridViewColumn.CellTemplate>
<DataTemplate>
<cc:MyEditDeleteButton x:Name="BoolToVisibility"
ImageSource="../Images/Edit.png"
Content="Edit"
Command="{Binding EditCommand}" DataContext="{Binding DataContext, RelativeSource={RelativeSource FindAncestor, AncestorType=ListView}}"
CommandParameter="{Binding Path=SelectedArticle.Id}"
Width="auto"/>
</DataTemplate>
</GridViewColumn.CellTemplate>
</GridViewColumn>
第二个StackPanel
<StackPanel Visibility="{Binding ElementName=BoolToVisibility,Path=IsChecked, Converter={ StaticResource BooleanToVisibilityConverter}}">
<Label Content="blablabla"></Label>
</StackPanel>
二手转换器:
<UserControl.Resources>
<BooleanToVisibilityConverter x:Key="BooleanToVisibilityConverter"/>
</UserControl.Resources>
我的自定义控件的类-Edit Button-继承自ToggleButton
public class MyEditDeleteButton : ToggleButton
{
static MyEditDeleteButton()
{
DefaultStyleKeyProperty.OverrideMetadata(typeof(MyEditDeleteButton), new FrameworkPropertyMetadata(typeof(MyEditDeleteButton)));
}
public ImageSource ImageSource
{
get { return (ImageSource)GetValue(ImageSourceProperty); }
set { SetValue(ImageSourceProperty, value); }
}
// Using a DependencyProperty as the backing store for ImageSource. This enables animation, styling, binding, etc...
public static readonly DependencyProperty ImageSourceProperty =
DependencyProperty.Register("ImageSource", typeof(ImageSource), typeof(MyEditDeleteButton), new UIPropertyMetadata(null));
}
所以,2个问题:
选择列表项目时,将在整个列中启用编辑按钮
单击编辑按钮时,显示第二个堆栈面板的可见性。
更新
谢谢你的回复。 问题没有完全解决,也许我做错了。 这是我做的:
@Ed Plunkett。我看不出如何声明_EditItem字段。
private Item _editItem;
你的意思是来自ViewModel的项目? 在我的视图模型中,我有一个没有参数的构造函数
Edit item = new Item (item);
<StackPanel>
<StackPanel>
... ListView with the Edit Button
</StackPanel>
<StackPanel Visibility="{Binding Mode=OneWay, Source={StaticResource StackCollapsed}}">
<Label Content="blablabla"></Label>
</StackPanel>
</StackPanel>
在App.xaml中:
<Application.Resources>
<BooleanToVisibilityConverter x:Key="BooleanToVisibilityConverter"/>
<Style x:Key="StackCollapsed" TargetType="StackPanel">
<Setter Property="Visibility" Value="Collapsed"/>
<Style.Triggers>
<DataTrigger Binding="{Binding Path=(viewModels:ArticleViewModel.IsEditable), Converter={ StaticResource BooleanToVisibilityConverter}}" Value="{x:Null}">
<Setter Property="Visibility" Value="Visible"/>
</DataTrigger>
</Style.Triggers>
</Style>
</Application.Resources>
我仍然看到StackPanel,它的可见性从未改变过。
答案 0 :(得分:0)
以下是我将如何做到这一点。
首先,为ViewModel提供一个带有EditItem
setter的protected
属性。它的类型是你的项目类型。当EditItem
为空时,隐藏编辑器区域。
<StackPanel.Style>
<Style TargetType="StackPanel">
<Style.Triggers>
<DataTrigger Binding="{Binding EditItem}" Value="{x:Null}">
<Setter Property="Visibility" Value="Collapsed" />
</DataTrigger>
</Style.Triggers>
</Style>
</StackPanel.Style>
我的EditItemCommand
在XAML中看起来和你的很相似:
<GridViewColumn.CellTemplate>
<DataTemplate>
<Button
Content="Edit"
Command="{Binding DataContext.EditItemCommand, RelativeSource={RelativeSource AncestorType=ListView}}"
CommandParameter="{Binding}"
IsEnabled="{Binding IsSelected, RelativeSource={RelativeSource AncestorType=ListViewItem}}"
/>
</DataTemplate>
</GridViewColumn.CellTemplate>
...但是在viewmodel中,它会将EditItem
设置为命令参数的克隆,并将命令参数存储在私有字段Item _editItemOriginal
中。
我不同意您决定仅为所选行启用“编辑”按钮。我让用户直接进入编辑按钮而不先点击该行。但这是你的电话,上面IsEnabled
中的CellTemplate
绑定说明了实现这一目标的简单方法。
我的SaveEditItemCommand
会使用其命令参数_editItemOriginal
的任何已编辑属性更新Item
。只有当CanExecute
参数的参数为Item
时,它的CancelEditCommand
代码才会返回true。
我的EditItem
会将_editItemOriginal
和null
设置为CanExecute
。同样,仅当Item
代码的参数为DelegateCommand
时,它才会返回true。
对于所有这些命令,我会使用CanExecuteChanged
类来让我明确地提出EditItem
。我的#region EditItem Property
private Item _editItem = null;
public Item EditItem
{
get { return _editItem; }
protected set
{
if (value != _editItem)
{
_editItem = value;
if (_editItem == null)
{
_editItemOriginal = null;
}
OnPropertyChanged();
EditItemCommand.RaiseCanExecuteChanged();
SaveItemCommand.RaiseCanExecuteChanged();
CancelEditCommand.RaiseCanExecuteChanged();
}
}
}
private Item _editItemOriginal;
protected void EditThisItem(Item item)
{
EditItem = new Item(item);
_editItemOriginal = item;
}
#endregion EditItem Property
制定者将负责:
"coordinates":{"0":{"received_at":1471529314,"lat":28.6888798,"long":77.3247225}}