using FWindSoft.Data;
using System.Collections.ObjectModel;
using System.Linq;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Input;
namespace FWindSoft.Wpf.Controls
{
/*
* 暂时先不支持内容给窗体赋值
*/
//[ContentProperty("WChildren")]
[TemplatePart(Name = PART_Child, Type = typeof(NavigationBar))]
public class NavigationBar : Control
{
#region 附加属性
///
/// 窗体启动参数,根据Parameter在load中初始化
///
public static readonly DependencyProperty ParameterProperty = DependencyProperty.RegisterAttached("Parameter",
typeof(NParameter), typeof(NavigationBar), new PropertyMetadata(null, null));
[AttachedPropertyBrowsableForType(typeof(NChildWindow))]
public static NParameter GetParameter(DependencyObject obj)
{
return obj.GetValue(ParameterProperty) as NParameter;
}
[AttachedPropertyBrowsableForType(typeof(NChildWindow))]
public static void SetParameter(DependencyObject obj, object value)
{
obj.SetValue(ParameterProperty, value);
}
#endregion
#region 静态信息管理
private static NavigationBar m_CurrentNavigation;
///
/// 当前导航信息
///
public static NavigationBar CurrentNavigation
{
get
{
if (m_CurrentNavigation == null)
{
m_CurrentNavigation = new NavigationBar();
}
return m_CurrentNavigation;
}
}
#endregion
static NavigationBar()
{
DefaultStyleKeyProperty.OverrideMetadata(typeof(NavigationBar),
new FrameworkPropertyMetadata(typeof(NavigationBar)));
Jump = new RoutedCommand("跳转", typeof(NavigationBar));
CommandManager.RegisterClassCommandBinding(typeof(NavigationBar), new CommandBinding(Jump, OnJumpCommand, CanExecuteJump));
GoBack = new RoutedCommand("返回", typeof(NavigationBar));
CommandManager.RegisterClassCommandBinding(typeof(NavigationBar), new CommandBinding(GoBack, OnGoBackCommand, CanExecuteGoBack));
}
public NavigationBar()
{
NavigationItems = new ReadOnlyObservableCollection(m_NavigationItems = new ObservableCollection());
}
public const string PART_Child = "PART_Child";
public override void OnApplyTemplate()
{
base.OnApplyTemplate();
ChildContainer = GetTemplateChild(PART_Child) as ScrollViewer;
}
private ScrollViewer ChildContainer{ get; set; }
#region 依赖属性
public static readonly DependencyProperty ShowWindowProperty = DependencyProperty.Register("ShowWindow",
typeof(NChildWindow),
typeof(NavigationBar), new PropertyMetadata(null, null));
///
/// 关联显示属性集合
///
internal NChildWindow ShowWindow
{
get { return (NChildWindow)GetValue(ShowWindowProperty); }
set { SetValue(ShowWindowProperty, value); }
}
private void RaiseChange()
{
ShowWindow = GetCurrentWindow();
//ShowWindow.InvalidateVisual();
this.GoBackVisible= this.NavigationItems != null && this.NavigationItems.Count > 1;
if (this.NavigationItems != null)
{
this.NavigationItems.ToList().ForEach(i => i.Refresh());
}
}
#endregion
#region 操作与队列相似
private ObservableCollection m_NavigationItems;
public ReadOnlyObservableCollection NavigationItems
{
get;
private set;
}
///
/// 添加导航项
///
///
private void AddNavigationItem(NavigationItem item)
{
this.m_NavigationItems.Add(item);
RaiseChange();
}
///
/// 移除导航项
///
///
private void RemoveNavigationItem(NavigationItem item)
{
var useItem = this.m_NavigationItems.LastOrDefault(p => p.Window ==item.Window);
if (useItem != null)
{
var index=this.m_NavigationItems.IndexOf(useItem);
var allItems = this.m_NavigationItems.ToList();
this.m_NavigationItems.Clear();
for (int i = 0; i < index; i++)
{
this.m_NavigationItems.Add(allItems[i]);
}
RaiseChange();
}
}
#endregion
/*
* 调用子窗体show方法,增加找到最近的一个赋值,也可以直接赋值
* 调用窗体的Close方法,移除找到最近的一个赋值
*
* 导航样式为:当前:A-->B-->C
*/
public void Remove(NChildWindow window)
{
var nParameter = GetParameter(window);
if (nParameter != null && nParameter.IsClear)
{
this.m_NavigationItems.Clear();
return;
}
RemoveNavigationItem(new NavigationItem(window));
}
public void Add(NChildWindow window)
{
var nParameter = GetParameter(window);
if (nParameter != null && nParameter.IsClear)
{
this.m_NavigationItems.Clear();
return;
}
AddNavigationItem(new NavigationItem(window));
// RaiseChange();
}
///
/// 获取当前的窗体
///
///
public NChildWindow GetCurrentWindow()
{
if (this.m_NavigationItems == null || !this.m_NavigationItems.Any())
return DefaultWindow;
return this.m_NavigationItems.LastOrDefault().Window;
}
///
/// 默认窗体
///
public NChildWindow DefaultWindow { get; set; }
#region 跳转命令相关
///
/// 跳转命令
///
public static RoutedCommand Jump { get; private set; }
private static void OnJumpCommand(object sender, ExecutedRoutedEventArgs e)
{
NavigationBar bar = sender as NavigationBar;
if (bar != null)
{
NavigationItem item = e.Parameter as NavigationItem;
//所谓跳转,移除跳转项目后面所有的选项
var index=bar.NavigationItems.IndexOf(item);
if (index < bar.NavigationItems.Count - 1)
{
bar.RemoveNavigationItem(bar.NavigationItems[index + 1]);
}
}
}
private static void CanExecuteJump(object sender, CanExecuteRoutedEventArgs e)
{
NavigationBar bar = sender as NavigationBar;
if (bar != null)
{
NavigationItem item = e.Parameter as NavigationItem;
if (item == null || bar.NavigationItems.Last() == item)
{
e.CanExecute = false;
return;
}
}
e.CanExecute = true;
}
#endregion
#region 返回相关
///
/// 跳转命令
///
public static RoutedCommand GoBack { get; private set; }
private static void OnGoBackCommand(object sender, ExecutedRoutedEventArgs e)
{
NavigationBar bar = sender as NavigationBar;
if (bar != null)
{
if (bar.NavigationItems != null && bar.NavigationItems.Count > 1)
{
NavigationItem item = bar.NavigationItems[bar.NavigationItems.Count - 2];
//所谓跳转,移除跳转项目后面所有的选项
var index = bar.NavigationItems.IndexOf(item);
if (index < bar.NavigationItems.Count - 1)
{
bar.RemoveNavigationItem(bar.NavigationItems[index + 1]);
}
}
}
}
private static void CanExecuteGoBack(object sender, CanExecuteRoutedEventArgs e)
{
NavigationBar bar = sender as NavigationBar;
if (bar != null)
{
e.CanExecute = bar.GoBackVisible;
}
e.CanExecute = true;
}
public static readonly DependencyProperty GoBackVisibleProperty = DependencyProperty.Register("GoBackVisible",
typeof(bool),
typeof(NavigationBar), new PropertyMetadata(false, null));
///
/// 关联显示属性集合
///
internal bool GoBackVisible
{
get { return (bool)GetValue(GoBackVisibleProperty); }
set { SetValue(GoBackVisibleProperty, value); }
}
#endregion
#region 逐步扩展
///
/// 刷新存量窗体的加载状态【延迟到显示是起作用】
///
public void RefreshWindows()
{
for (int i = 0; i < this.m_NavigationItems.Count; i++)
{
var item = this.m_NavigationItems[i];
item.Window?.ResetLoadData();
}
}
///
/// 刷新上一个窗体状态
///
public void RefreshPreWinddow()
{
if (this.NavigationItems != null && this.NavigationItems.Count > 1)
{
NavigationItem item = this.NavigationItems[this.NavigationItems.Count - 2];
item.Window.ResetLoadData();
}
}
#endregion
protected override void OnPreviewMouseWheel(MouseWheelEventArgs e)
{
base.OnPreviewMouseWheel(e);
if (ChildContainer != null)
{
var uiElement = e.OriginalSource as UIElement;
if (uiElement == null)
{
return;
}
var useScroll=uiElement.GetParentTypeSelf();
while (useScroll != null && useScroll.ComputedVerticalScrollBarVisibility == Visibility.Collapsed)
{
useScroll = useScroll.GetParentType();
}
if (useScroll == ChildContainer)
{
var eventArg = new MouseWheelEventArgs(e.MouseDevice, e.Timestamp, e.Delta);
eventArg.RoutedEvent = UIElement.MouseWheelEvent;
eventArg.Source = this;
ChildContainer.RaiseEvent(eventArg);
}
}
}
}
///
/// 封装操作实体,直接将控件绑定到Items,将出现可是话树重叠的情况
///
public class NavigationItem:BasePropertyChanged
{
internal NavigationItem(NChildWindow window)
{
this.Window = window;
}
internal NavigationItem()
{
}
public void Refresh()
{
RaisePropertyChanged(nameof(WindowDisplay));
}
///
/// 导航窗体使用参数
///
//public NParameter NParameter { get; set; }
///
/// 关联窗体
///
public NChildWindow Window { get; set; }
///
/// 窗体描述
///
public string WindowDisplay
{
get
{
if (Window == null)
return "Null";
return Window.Title;
}
}
}
}