积极答复者
win8 应用商店开发中,如何通过button绑定事件又后台去处理xaml中用户输入的用户名和帐号是否正确?

问题
-
我在xamL中定义了一个button:
<Button x:Name="btnOK" Style="{StaticResource OKCancelButtonStyle}" Grid.Column="1" HorizontalAlignment="Left">
<Button.Content>
<Grid>
<Image Source="/Assets/Images/Icons/button_ok.png" Stretch="None"/>
<TextBlock Text="OK" Style="{StaticResource Size32TextBlock}"/>
</Grid>
</Button.Content>
<inter:Interaction.Triggers>
<inter:EventTrigger EventName="Click">
<inter:InvokeCommandAction Command="{Binding BtnOKCommand}" CommandParameter="{Binding ElementName=btnOK}"/>//这里如何把本页面的用户在nameTextBox中输入的名字,和passwordTextBox中的密码一起传到后台的BtnOKCommand方法中进行判断名字和密码是否正确?正确再转入我想进人多页面...
</inter:EventTrigger>
</inter:Interaction.Triggers>
</Button>下面是后台BtnOKCommand的定义
private RelayCommand<RoutedEventArgs> btnOKCommand;
public RelayCommand<RoutedEventArgs> BtnOKCommand
{
get
{
return btnOKCommand ?? (btnOKCommand = new RelayCommand<RoutedEventArgs>((args) => BtnOK(args)));
}
}object BtnOK(RoutedEventArgs args)
{//是在这里写还是在哪里怎么写,对那个页面的内容进行判断?
Helpers.NavigateHelper.Navigate(typeof(Views.Main.MainPage));return null;
}先谢谢了
- 已移动 Lisa Zhu 2013年3月22日 5:00 Win8 应用商店应用
答案
-
解决方案可以变换下思维,不一定非要传2个参数过去,虽然是可以的。提供你几个思路
1.用户名 密码直接绑定到vm中的属性
2.点击Button时,先使用ChangePropertyAction改变vm的属性值之后,再进行InvokeCommandAction,此时直接利用属性值进行判断
3.如你所说的,传2个参数过去。
(1)首先定义Command
public class DelegateCommand<T> : ICommand where T : class { Action<T> m_excuteAction; Func<T, bool> m_canExcunteFunc; /// <summary> /// 构造函数 /// </summary> /// <param name="excuteAction"></param> public DelegateCommand(Action<T> excuteAction) { m_excuteAction = excuteAction; } /// <summary> /// 构造函数 /// </summary> /// <param name="excuteAction"></param> /// <param name="canExcuteAction"></param> public DelegateCommand(Action<T> excuteAction, Func<T, bool> canExcuteAction) { m_canExcunteFunc = canExcuteAction; m_excuteAction = excuteAction; } private bool m_isCanExecute = true; public bool IsCanExecute { get { return m_isCanExecute; } set { if (value != m_isCanExecute) { m_isCanExecute = value; FireCanExecuteChanged(); } } } private void FireCanExecuteChanged() { if (CanExecuteChanged != null) CanExecuteChanged(this, new EventArgs()); } #region ICommand Members public bool CanExecute(object parameter) { if (m_canExcunteFunc == null) { return IsCanExecute; } else { T args; args = parameter as T; IsCanExecute = m_canExcunteFunc(args); } return IsCanExecute; } public event EventHandler CanExecuteChanged; public void Execute(object parameter) { if (m_excuteAction != null) { T args; args = parameter as T; m_excuteAction(args); } } #endregion }
(2),定义参数类
[ContentProperty("Value")] public class CommandArg : DependencyObject, IEquatable<CommandArg> { public CommandArg(string key, Object value) { this.Key = key; this.Value = value; } public CommandArg() { } private const string KEY_CAN_NOT_NULL = "绑定参数的key不能为空"; #region DependencyProperty private static readonly DependencyProperty KeyProperty = DependencyProperty.Register("Key", typeof(string), typeof(CommandArg), new PropertyMetadata(new Random().Next().ToString(), KeyPropertyChanged)); private static readonly DependencyProperty ValueProperty = DependencyProperty.Register("Value", typeof(Object), typeof(CommandArg), new PropertyMetadata(null)); private static void KeyPropertyChanged(DependencyObject o, DependencyPropertyChangedEventArgs e) { if (string.IsNullOrWhiteSpace(Convert.ToString(e.NewValue)) && string.IsNullOrEmpty(Convert.ToString(e.NewValue))) throw new Exception(KEY_CAN_NOT_NULL); } bool m_isSetKey = false; public string Key { get { return Convert.ToString(GetValue(KeyProperty)); } set { if (string.IsNullOrWhiteSpace(Convert.ToString(value))) { throw new ArgumentException(KEY_CAN_NOT_NULL); } else { if (m_isSetKey == false) { SetValue(KeyProperty, value); m_isSetKey = true; } else { throw new InvalidOperationException("KEY_HAS_BEEN_SET"); } } } } public Object Value { get { return GetValue(ValueProperty); } set { SetValue(ValueProperty, value); } } #endregion public override string ToString() { return string.Format("({0},{1})", this.Key, this.Value); } #region IEquatable接口实现 public bool Equals(CommandArg other) { if (other == null) return false; return string.Equals(Key, other.Key, StringComparison.InvariantCultureIgnoreCase) && Value == other.Value; } #endregion }
(3),定义参数列表类
public class CommandArgs : DependencyObjectCollection<CommandArg> { public CommandArgs() : base() { base.Clear(); base.CollectionChanged += new NotifyCollectionChangedEventHandler(CommandArgs_CollectionChanged); } void CommandArgs_CollectionChanged(object sender, NotifyCollectionChangedEventArgs e) { if (e.Action == NotifyCollectionChangedAction.Add && e.NewItems != null) { foreach (CommandArg arg in e.NewItems) { CommandArg containArg = GetItemByKey(arg.Key); if (containArg != null && !containArg.Equals(arg)) { throw new Exception("The collection contains this key"); } } } } public new void SetValue(DependencyProperty dp, object value) { //System.Diagnostics.Debug.WriteLine("SetValue"); base.SetValue(dp, value); } public bool Contains(string key) { if (GetItemByKey(key) == null) { return false; } else { return true; } } public new void Add(CommandArg item) { if (GetItemByKey(item.Key) != null) { throw new Exception("The collection contains this key"); } else { base.Add(item); } } private CommandArg GetItemByKey(string key) { if (!String.IsNullOrEmpty(key) && !String.IsNullOrWhiteSpace(key)) { for (int i = 0; i < base.Count; i++) { CommandArg arg = base[i]; if (arg.Key == key) { return arg; } } } return null; } /// <summary> /// 索引器 /// </summary> /// <param name="key">Key</param> /// <returns></returns> public CommandArg this[string key] { get { return GetItemByKey(key); } set { CommandArg arg = GetItemByKey(key); if (arg == null) { throw new NullReferenceException(); } else { arg = value; } } } }
(4),调用方法
<i:Interaction.Triggers> <i:EventTrigger EventName="Tap"> <i:InvokeCommandAction Command="{Binding ClickImageCommand}"> <i:InvokeCommandAction.CommandParameter> <Command:CommandArgs> <Command:CommandArg Key="a" Value="{Binding Text,ElementName=txttest}"></Command:CommandArg> <Command:CommandArg Key="b" Value="2"></Command:CommandArg> </Command:CommandArgs> </i:InvokeCommandAction.CommandParameter> </i:InvokeCommandAction> </i:EventTrigger> </i:Interaction.Triggers>
(5) vm中
public ICommand ClickImageCommand { get; set; } ClickImageCommand = new DelegateCommand<CommandArgs>(ClickImage); private void ClickImage(CommandArgs args) { foreach (CommandArg item in args) { string key = item.Key; object content = item.Value; } }
Big Big Pig.
- 已标记为答案 Aaron XueModerator 2013年3月28日 9:50
-
我个人的处理方式是将两个或者多个参数封装入 object[] 数组,然后将其传递给 RelayCommand<T>
public class AttachedCommand { public static string GetRoutedEvent(DependencyObject obj) { return (string)obj.GetValue(RoutedEventProperty); } public static void SetRoutedEvent(DependencyObject obj, string value) { obj.SetValue(RoutedEventProperty, value); } public static readonly DependencyProperty RoutedEventProperty = DependencyProperty.RegisterAttached("RoutedEvent", typeof(string), typeof(AttachedCommand), new PropertyMetadata(string.Empty, OnRoutedEventChanged)); public static ICommand GetCommand(DependencyObject obj) { return (ICommand)obj.GetValue(CommandProperty); } public static void SetCommand(DependencyObject obj, ICommand value) { obj.SetValue(CommandProperty, value); } public static readonly DependencyProperty CommandProperty = DependencyProperty.RegisterAttached("Command", typeof(ICommand), typeof(AttachedCommand), new PropertyMetadata(null)); public static object GetCommandParameter(DependencyObject obj) { return (object)obj.GetValue(CommandParameterProperty); } public static void SetCommandParameter(DependencyObject obj, object value) { obj.SetValue(CommandParameterProperty, value); } public static readonly DependencyProperty CommandParameterProperty = DependencyProperty.RegisterAttached("CommandParameter", typeof(object), typeof(AttachedCommand), new PropertyMetadata(null)); private static void OnRoutedEventChanged(DependencyObject d, DependencyPropertyChangedEventArgs e) { String routedevent = (String)e.NewValue; if (!String.IsNullOrEmpty(routedevent)) { EventHooker eventHooker = new EventHooker(); eventHooker.AttachedCommandObject = d; EventInfo eventInfo = d.GetType().GetTypeInfo().GetMemberInfo(routedevent, MemberType.Event) as EventInfo; if (eventInfo != null) { WindowsRuntimeMarshal.RemoveAllEventHandlers( a => eventInfo.RemoveMethod.Invoke(d, new object[] { a })); WindowsRuntimeMarshal.AddEventHandler( f => (EventRegistrationToken)eventInfo.AddMethod.Invoke(d, new object[] { f }), a => eventInfo.RemoveMethod.Invoke(d, new object[] { a }), eventHooker.GetEventHandler(eventInfo)); } } } internal sealed class EventHooker { public DependencyObject AttachedCommandObject { get; set; } public Delegate GetEventHandler(EventInfo eventInfo) { Delegate del = null; if (eventInfo == null) throw new ArgumentNullException("eventInfo"); if (eventInfo.EventHandlerType == null) throw new ArgumentNullException("eventInfo.EventHandlerType"); if (del == null) del = this.GetType().GetTypeInfo().GetDeclaredMethod("OnEventRaised").CreateDelegate(eventInfo.EventHandlerType, this); return del; } private void OnEventRaised(object sender, object e) // the second parameter in Windows.UI.Xaml.EventHandler is Object { ICommand command = (ICommand)(sender as DependencyObject).GetValue(AttachedCommand.CommandProperty); object commandParameter = (sender as DependencyObject).GetValue(AttachedCommand.CommandParameterProperty); if (commandParameter == null) commandParameter = new object[] { sender, e }; else commandParameter = new object[] { sender, e, commandParameter }; // 关键这里 if (command != null && command.CanExecute(commandParameter)) { command.Execute(commandParameter); } } } }
Bob Bao
Do you still use the same Windows 8 LockScreen always? Download Chameleon Win8 App quickly, that changes your LockScreen constantly.
你是否还在看着一成不变的Windows 8锁屏而烦恼,赶紧下载这个 百变锁屏 应用,让你的锁屏不断地变化起来。- 已标记为答案 Aaron XueModerator 2013年3月28日 9:50
全部回复
-
Hi,
你确定你开发的是应用商店程序?Windows应用商店中并没有trigger。而且你的导航页面的代码似乎也不对。最好是能够把app代码分享到SkyDrive上。
Aaron
MSDN Community Support | Feedback to us
Develop and promote your apps in Windows Store
Please remember to mark the replies as answers if they help and unmark them if they provide no help. -
解决方案可以变换下思维,不一定非要传2个参数过去,虽然是可以的。提供你几个思路
1.用户名 密码直接绑定到vm中的属性
2.点击Button时,先使用ChangePropertyAction改变vm的属性值之后,再进行InvokeCommandAction,此时直接利用属性值进行判断
3.如你所说的,传2个参数过去。
(1)首先定义Command
public class DelegateCommand<T> : ICommand where T : class { Action<T> m_excuteAction; Func<T, bool> m_canExcunteFunc; /// <summary> /// 构造函数 /// </summary> /// <param name="excuteAction"></param> public DelegateCommand(Action<T> excuteAction) { m_excuteAction = excuteAction; } /// <summary> /// 构造函数 /// </summary> /// <param name="excuteAction"></param> /// <param name="canExcuteAction"></param> public DelegateCommand(Action<T> excuteAction, Func<T, bool> canExcuteAction) { m_canExcunteFunc = canExcuteAction; m_excuteAction = excuteAction; } private bool m_isCanExecute = true; public bool IsCanExecute { get { return m_isCanExecute; } set { if (value != m_isCanExecute) { m_isCanExecute = value; FireCanExecuteChanged(); } } } private void FireCanExecuteChanged() { if (CanExecuteChanged != null) CanExecuteChanged(this, new EventArgs()); } #region ICommand Members public bool CanExecute(object parameter) { if (m_canExcunteFunc == null) { return IsCanExecute; } else { T args; args = parameter as T; IsCanExecute = m_canExcunteFunc(args); } return IsCanExecute; } public event EventHandler CanExecuteChanged; public void Execute(object parameter) { if (m_excuteAction != null) { T args; args = parameter as T; m_excuteAction(args); } } #endregion }
(2),定义参数类
[ContentProperty("Value")] public class CommandArg : DependencyObject, IEquatable<CommandArg> { public CommandArg(string key, Object value) { this.Key = key; this.Value = value; } public CommandArg() { } private const string KEY_CAN_NOT_NULL = "绑定参数的key不能为空"; #region DependencyProperty private static readonly DependencyProperty KeyProperty = DependencyProperty.Register("Key", typeof(string), typeof(CommandArg), new PropertyMetadata(new Random().Next().ToString(), KeyPropertyChanged)); private static readonly DependencyProperty ValueProperty = DependencyProperty.Register("Value", typeof(Object), typeof(CommandArg), new PropertyMetadata(null)); private static void KeyPropertyChanged(DependencyObject o, DependencyPropertyChangedEventArgs e) { if (string.IsNullOrWhiteSpace(Convert.ToString(e.NewValue)) && string.IsNullOrEmpty(Convert.ToString(e.NewValue))) throw new Exception(KEY_CAN_NOT_NULL); } bool m_isSetKey = false; public string Key { get { return Convert.ToString(GetValue(KeyProperty)); } set { if (string.IsNullOrWhiteSpace(Convert.ToString(value))) { throw new ArgumentException(KEY_CAN_NOT_NULL); } else { if (m_isSetKey == false) { SetValue(KeyProperty, value); m_isSetKey = true; } else { throw new InvalidOperationException("KEY_HAS_BEEN_SET"); } } } } public Object Value { get { return GetValue(ValueProperty); } set { SetValue(ValueProperty, value); } } #endregion public override string ToString() { return string.Format("({0},{1})", this.Key, this.Value); } #region IEquatable接口实现 public bool Equals(CommandArg other) { if (other == null) return false; return string.Equals(Key, other.Key, StringComparison.InvariantCultureIgnoreCase) && Value == other.Value; } #endregion }
(3),定义参数列表类
public class CommandArgs : DependencyObjectCollection<CommandArg> { public CommandArgs() : base() { base.Clear(); base.CollectionChanged += new NotifyCollectionChangedEventHandler(CommandArgs_CollectionChanged); } void CommandArgs_CollectionChanged(object sender, NotifyCollectionChangedEventArgs e) { if (e.Action == NotifyCollectionChangedAction.Add && e.NewItems != null) { foreach (CommandArg arg in e.NewItems) { CommandArg containArg = GetItemByKey(arg.Key); if (containArg != null && !containArg.Equals(arg)) { throw new Exception("The collection contains this key"); } } } } public new void SetValue(DependencyProperty dp, object value) { //System.Diagnostics.Debug.WriteLine("SetValue"); base.SetValue(dp, value); } public bool Contains(string key) { if (GetItemByKey(key) == null) { return false; } else { return true; } } public new void Add(CommandArg item) { if (GetItemByKey(item.Key) != null) { throw new Exception("The collection contains this key"); } else { base.Add(item); } } private CommandArg GetItemByKey(string key) { if (!String.IsNullOrEmpty(key) && !String.IsNullOrWhiteSpace(key)) { for (int i = 0; i < base.Count; i++) { CommandArg arg = base[i]; if (arg.Key == key) { return arg; } } } return null; } /// <summary> /// 索引器 /// </summary> /// <param name="key">Key</param> /// <returns></returns> public CommandArg this[string key] { get { return GetItemByKey(key); } set { CommandArg arg = GetItemByKey(key); if (arg == null) { throw new NullReferenceException(); } else { arg = value; } } } }
(4),调用方法
<i:Interaction.Triggers> <i:EventTrigger EventName="Tap"> <i:InvokeCommandAction Command="{Binding ClickImageCommand}"> <i:InvokeCommandAction.CommandParameter> <Command:CommandArgs> <Command:CommandArg Key="a" Value="{Binding Text,ElementName=txttest}"></Command:CommandArg> <Command:CommandArg Key="b" Value="2"></Command:CommandArg> </Command:CommandArgs> </i:InvokeCommandAction.CommandParameter> </i:InvokeCommandAction> </i:EventTrigger> </i:Interaction.Triggers>
(5) vm中
public ICommand ClickImageCommand { get; set; } ClickImageCommand = new DelegateCommand<CommandArgs>(ClickImage); private void ClickImage(CommandArgs args) { foreach (CommandArg item in args) { string key = item.Key; object content = item.Value; } }
Big Big Pig.
- 已标记为答案 Aaron XueModerator 2013年3月28日 9:50
-
我个人的处理方式是将两个或者多个参数封装入 object[] 数组,然后将其传递给 RelayCommand<T>
public class AttachedCommand { public static string GetRoutedEvent(DependencyObject obj) { return (string)obj.GetValue(RoutedEventProperty); } public static void SetRoutedEvent(DependencyObject obj, string value) { obj.SetValue(RoutedEventProperty, value); } public static readonly DependencyProperty RoutedEventProperty = DependencyProperty.RegisterAttached("RoutedEvent", typeof(string), typeof(AttachedCommand), new PropertyMetadata(string.Empty, OnRoutedEventChanged)); public static ICommand GetCommand(DependencyObject obj) { return (ICommand)obj.GetValue(CommandProperty); } public static void SetCommand(DependencyObject obj, ICommand value) { obj.SetValue(CommandProperty, value); } public static readonly DependencyProperty CommandProperty = DependencyProperty.RegisterAttached("Command", typeof(ICommand), typeof(AttachedCommand), new PropertyMetadata(null)); public static object GetCommandParameter(DependencyObject obj) { return (object)obj.GetValue(CommandParameterProperty); } public static void SetCommandParameter(DependencyObject obj, object value) { obj.SetValue(CommandParameterProperty, value); } public static readonly DependencyProperty CommandParameterProperty = DependencyProperty.RegisterAttached("CommandParameter", typeof(object), typeof(AttachedCommand), new PropertyMetadata(null)); private static void OnRoutedEventChanged(DependencyObject d, DependencyPropertyChangedEventArgs e) { String routedevent = (String)e.NewValue; if (!String.IsNullOrEmpty(routedevent)) { EventHooker eventHooker = new EventHooker(); eventHooker.AttachedCommandObject = d; EventInfo eventInfo = d.GetType().GetTypeInfo().GetMemberInfo(routedevent, MemberType.Event) as EventInfo; if (eventInfo != null) { WindowsRuntimeMarshal.RemoveAllEventHandlers( a => eventInfo.RemoveMethod.Invoke(d, new object[] { a })); WindowsRuntimeMarshal.AddEventHandler( f => (EventRegistrationToken)eventInfo.AddMethod.Invoke(d, new object[] { f }), a => eventInfo.RemoveMethod.Invoke(d, new object[] { a }), eventHooker.GetEventHandler(eventInfo)); } } } internal sealed class EventHooker { public DependencyObject AttachedCommandObject { get; set; } public Delegate GetEventHandler(EventInfo eventInfo) { Delegate del = null; if (eventInfo == null) throw new ArgumentNullException("eventInfo"); if (eventInfo.EventHandlerType == null) throw new ArgumentNullException("eventInfo.EventHandlerType"); if (del == null) del = this.GetType().GetTypeInfo().GetDeclaredMethod("OnEventRaised").CreateDelegate(eventInfo.EventHandlerType, this); return del; } private void OnEventRaised(object sender, object e) // the second parameter in Windows.UI.Xaml.EventHandler is Object { ICommand command = (ICommand)(sender as DependencyObject).GetValue(AttachedCommand.CommandProperty); object commandParameter = (sender as DependencyObject).GetValue(AttachedCommand.CommandParameterProperty); if (commandParameter == null) commandParameter = new object[] { sender, e }; else commandParameter = new object[] { sender, e, commandParameter }; // 关键这里 if (command != null && command.CanExecute(commandParameter)) { command.Execute(commandParameter); } } } }
Bob Bao
Do you still use the same Windows 8 LockScreen always? Download Chameleon Win8 App quickly, that changes your LockScreen constantly.
你是否还在看着一成不变的Windows 8锁屏而烦恼,赶紧下载这个 百变锁屏 应用,让你的锁屏不断地变化起来。- 已标记为答案 Aaron XueModerator 2013年3月28日 9:50