如有:
<Window x:Class="AVA.Meeting.Client.View.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
Height="900" Width="800" MinWidth="800" MinHeight="500" Closed="{Binding OnClose}">
有CS public ICommand OnClose { get; set; } public void Close(string paranper)
{
if (Service.ServiceClient.Instance != null)
{
Service.ServiceClient.Instance.Leave();
Service.ServiceClient.Instance.Close();
Service.ServiceClient.Instance = null;
}
//this.window.Close();
}
但绑定运行后出错:
在“System.Windows.Data.Binding”上提供值时引发了异常。”
{"无法将类型为“System.Reflection.RuntimeEventInfo”的对象强制转换为类型“System.Reflection.MethodInfo”。"}
<Window x:Class="AVA.Meeting.Client.View.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
Height="900" Width="800" MinWidth="800" MinHeight="500" Closed="{Binding OnClose}">
有CS public ICommand OnClose { get; set; } public void Close(string paranper)
{
if (Service.ServiceClient.Instance != null)
{
Service.ServiceClient.Instance.Leave();
Service.ServiceClient.Instance.Close();
Service.ServiceClient.Instance = null;
}
//this.window.Close();
}
但绑定运行后出错:
在“System.Windows.Data.Binding”上提供值时引发了异常。”
{"无法将类型为“System.Reflection.RuntimeEventInfo”的对象强制转换为类型“System.Reflection.MethodInfo”。"}
解决方案 »
- |ZYCWPF| WebBrowser 在什么时候对img标签进行拦截显示,有详细说明
- 【一百分结贴】这段代码无法释放内存吗?
- c#类的实例化出错
- 怎么让一个Button有两个点击事件?
- 求最高效的矢量数据 光栏法 压缩算法代码
- 怎样把Excel文件本身存入SQL Server数据库,又怎样查出后显示在Form上
- ConfigurationManager.AppSettings的问题,各位帮忙!
- 如何使某段代码在MainForm完全呈现后再执行?(C#)
- 数据库建模工具哪个性能、功能好?erwin4.1?powerdesigner10?rose2003?其它?请教
- 各位前辈,请指教
- 关于Paint事件 绑定数据显示延迟问题
- 计算最小距离
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"
Height="900" Width="800" MinWidth="800" MinHeight="500">
<i:Interaction.Triggers>
<i:EventTrigger EventName="Closed">
<i:InvokeCommandAction Command="{Binding OnClose}" />
</i:EventTrigger>
</i:Interaction.Triggers>
... ...如果需要这样处理事件的地方很多的话,都像上面这样写xaml就会比较繁复。所以不如干脆直接在code behind类里写事件处理方法,让xaml看上去简单些。比如: public MainWindow()
{
this.DataContext = new ViewModel.MainWindowViewModel(this);
InitializeComponent();
this.Closed += (o, args) => ((MainWindowViewModel) DataContext).OnClose.Execute(null);
}我知道网上有些人主张code behind类应该是"0代码"。虽然我个人觉得没必要这么教条,不过如果你不想在code behind类里写代码的话,也可以写一个attached property来简化执行事件命令的xaml标记写法。
attached property的写法我在前一个帖子写过:http://bbs.csdn.net/topics/390271219
把里面的CommandAction类KeyDown相关的部分改成Closed,就能把它变成在Closed事件触发时执行command命令。上面帖子里的这个方法还可以进一步改进成通用的基类,方便任意事件对其进行扩展使用: public class EventCommand<T> where T:EventCommand<T>, new()
{
public static DependencyProperty CommandProperty =
DependencyProperty.RegisterAttached("Command", typeof (ICommand), typeof (EventCommand<T>),
new UIPropertyMetadata(OnCommandChanged)); private static Action<UIElement> _addHandler;
private static Action<UIElement> _removeHandler; public static void Register<TOwner>(Action<TOwner> addHandler, Action<TOwner> removeHandler)
where TOwner : UIElement
{
_addHandler = x=> addHandler((TOwner)x);
_removeHandler = x => removeHandler((TOwner)x);
} public static void Register(RoutedEvent @event, Func<Delegate> handler = null)
{
handler = handler ?? (()=>new RoutedEventHandler(InvokeCommand));
_addHandler = x => x.AddHandler(@event, handler());
_removeHandler = x=> x.RemoveHandler(@event, handler());
} public static void SetCommand(UIElement target, ICommand value)
{
target.SetValue(CommandProperty, value);
} private static T _me;
private static void OnCommandChanged(DependencyObject target, DependencyPropertyChangedEventArgs e)
{
if (_me == null) _me = new T(); // ensure event and handlers are registered
var element = target as UIElement;
if (element == null)
throw new InvalidOperationException("This behavior can be attached to ui element only.");
if (e.NewValue != null && e.OldValue == null)
_addHandler(element);
else if (e.NewValue == null && e.OldValue != null)
_removeHandler(element);
} protected static void InvokeCommand(object sender, EventArgs e)
{
var command = (ICommand) ((FrameworkElement)sender).GetValue(CommandProperty);
command.Execute(e);
}
} public class KeyDown : EventCommand<KeyDown> { static KeyDown() { Register(UIElement.KeyDownEvent); }}
public class KeyUp : EventCommand<KeyUp> { static KeyUp() { Register(UIElement.KeyUpEvent); }}
public class GotFocus : EventCommand<GotFocus> { static GotFocus() { Register(UIElement.GotFocusEvent); }}
public class LostFocus : EventCommand<LostFocus> { static LostFocus() { Register(UIElement.LostFocusEvent); }}
public class Closed : EventCommand<Closed> {
static Closed() { Register<Window>(x=>x.Closed+=InvokeCommand, x=>x.Closed-=InvokeCommand); }
}EventCommand就是和上面帖子里差不多的附加属性类,下面的KeyDown,KeyUp,GotFocus,LostFocus这些派生子类具体定义了事件类型和处理方式。按照上面的写法可以很方便地再添加其它种类的事件。
前台用法:<Window x:Class="AVA.Meeting.Client.View.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:local="clr-namespace:AVA.Meeting.SomeUtilityNameSpace"
local:Closed.Command="{Binding OnClose}"
Height="900" Width="800" MinWidth="800" MinHeight="500">
或者比如:
<TextBox local:KeyDown.Command="{Binding OnKeyDown}"
local:GotFocus.Command="{Binding OnGotFocus}"
local:LostFocus.Command="{Binding OnLostFocus}">
注意这样执行的命令是传递事件参数的,所以你的OnClose命令不能是string参数类型,在你的BindEvent方法里要写成:this.OnClose = new DelegateCommand<EventArgs>(Close);