using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows;
using System.Windows.Media.Imaging;
using Tango.BL.Entities;
using Tango.BL.Enumerations;
namespace Tango.MachineStudio.Common
{
/// <summary>
/// Represents a Machine Studio module.
/// </summary>
/// <seealso cref="System.IDisposable" />
public interface IStudioModule : IDisposable
{
/// <summary>
/// Gets the module name.
/// </summary>
String Name { get; }
/// <summary>
/// Gets the module description.
/// </summary>
String Description { get; }
/// <summary>
/// Gets the module cover image.
/// </summary>
BitmapSource Image { get; }
/// <summary>
/// Gets the module entry point view type.
/// </summary>
Type MainViewType { get; }
/// <summary>
/// Gets or sets a value indicating whether this module is shown under a new window.
/// </summary>
bool InNewWindow { get; set; }
/// <summary>
/// Gets the permission required to see and load this module.
/// </summary>
Permissions Permission { get; }
/// <summary>
/// Gets a value indicating whether this module has been initialized.
/// </summary>
bool IsInitialized { get; }
/// <summary>
/// Perform any operations required to initialize this module.
/// </summary>
void Initialize();
/// <summary>
/// Sets a value indicating whether this module is loaded.
pre { line-height: 125%; }
td.linenos .normal { color: inherit; background-color: transparent; padding-left: 5px; padding-right: 5px; }
span.linenos { color: inherit; background-color: transparent; padding-left: 5px; padding-right: 5px; }
td.linenos .special { color: #000000; background-color: #ffffc0; padding-left: 5px; padding-right: 5px; }
span.linenos.special { color: #000000; background-color: #ffffc0; padding-left: 5px; padding-right: 5px; }
.highlight .hll { background-color: #ffffcc }
.highlight .c { color: #888888 } /* Comment */
.highlight .err { color: #a61717; background-color: #e3d2d2 } /* Error */
.highlight .k { color: #008800; font-weight: bold } /* Keyword */
.highlight .ch { color: #888888 } /* Comment.Hashbang */
.highlight .cm { color: #888888 } /* Comment.Multiline */
.highlight .cp { color: #cc0000; font-weight: bold } /* Comment.Preproc */
.highlight .cpf { color: #888888 } /* Comment.PreprocFile */
.highlight .c1 { color: #888888 } /* Comment.Single */
.highlight .cs { color: #cc0000; font-weight: bold; background-color: #fff0f0 } /* Comment.Special */
.highlight .gd { color: #000000; background-color: #ffdddd } /* Generic.Deleted */
.highlight .ge { font-style: italic } /* Generic.Emph */
.highlight .ges { font-weight: bold; font-style: italic } /* Generic.EmphStrong */
.highlight .gr { color: #aa0000 } /* Generic.Error */
.highlight .gh { color: #333333 } /* Generic.Heading */
.highlight .gi { color: #000000; background-color: #ddffdd } /* Generic.Inserted */
.highlight .go { color: #888888 } /* Generic.Output */
.highlight .gp { color: #555555 } /* Generic.Prompt */
.highlight .gs { font-weight: bold } /* Generic.Strong */
.highlight .gu { color: #666666 } /* Generic.Subheading */
.highlight .gt { color: #aa0000 } /* Generic.Traceback */
.highlight .kc { color: #008800; font-weight: bold } /* Keyword.Constant */
.highlight .kd { color: #008800; font-weight: bold } /* Keyword.Declaration */
.highlight .kn { color: #008800; font-weight: bold } /* Keyword.Namespace */
.highlight .kp { color: #008800 } /* Keyword.Pseudo */
.highlight .kr { color: #008800; font-weight: bold } /* Keyword.Reserved */
.highlight .kt { color: #888888; font-weight: bold } /* Keyword.Type */
.highlight .m { color: #0000DD; font-weight: bold } /* Literal.Number */
.highlight .s { color: #dd2200; background-color: #fff0f0 } /* Literal.String */
.highlight .na { color: #336699 } /* Name.Attribute */
.highlight .nb { color: #003388 } /* Name.Builtin */
.highlight .nc { color: #bb0066; font-weight: bold } /* Name.Class */
.highlight .no { color: #003366; font-weight: bold } /* Name.Constant */
.highlight .nd { color: #555555 } /* Name.Decorator */
.highlight .ne { color: #bb0066; font-weight: bold } /* Name.Exception */
.highlight .nf { color: #0066bb; font-weight: bold } /* Name.Function */
.highlight .nl { color: #336699; font-style: italic } /* Name.Label */
.highlight .nn { color: #bb0066; font-weight: bold } /* Name.Namespace */
.highlight .py { color: #336699; font-weight: bold } /* Name.Property */
.highlight .nt { color: #bb0066; font-weight: bold } /* Name.Tag */
.highlight .nv { color: #336699 } /* Name.Variable */
.highlight .ow { color: #008800 } /* Operator.Word */
.highlight .w { color: #bbbbbb } /* Text.Whitespace */
.highlight .mb { color: #0000DD; font-weight: bold } /* Literal.Number.Bin */
.highlight .mf { color: #0000DD; font-weight: bold } /* Literal.Number.Float */
.highlight .mh { color: #0000DD; font-weight: bold } /* Literal.Number.Hex */
.highlight .mi { color: #0000DD; font-weight: bold } /* Literal.Number.Integer */
.highlight .mo { color: #0000DD; font-weight: bold } /* Literal.Number.Oct */
.highlight .sa { color: #dd2200; background-color: #fff0f0 } /* Literal.String.Affix */
.highlight .sb { color: #dd2200; background-color: #fff0f0 } /* Literal.String.Backtick */
.highlight .sc { color: #dd2200; background-color: #fff0f0 } /* Literal.String.Char */
.highlight .dl { color: #dd2200; background-color: #fff0f0 } /* Literal.String.Delimiter */
.highlight .sd { color: #dd2200; background-color: #fff0f0 } /* Literal.String.Doc */
.highlight .s2 { color: #dd2200; background-color: #fff0f0 } /* Literal.String.Double */
.highlight .se { color: #0044dd; background-color: #fff0f0 } /* Literal.String.Escape */
.highlight .sh { color: #dd2200; background-color: #fff0f0 } /* Literal.String.Heredoc */
.highlight .si { color: #3333bb; background-color: #fff0f0 } /* Literal.String.Interpol */
.highlight .sx { color: #22bb22; background-color: #f0fff0 } /* Literal.String.Other */
.highlight .sr { color: #008800; background-color: #fff0ff } /* Literal.String.Regex */
.highlight .s1 { color: #dd2200; background-color: #fff0f0 } /* Literal.String.Single */
.highlight .ss { color: #aa6600; background-color: #fff0f0 } /* Literal.String.Symbol */
.highlight .bp { color: #003388 } /* Name.Builtin.Pseudo */
.highlight .fm { color: #0066bb; font-weight: bold } /* Name.Function.Magic */
.highlight .vc { color: #336699 } /* Name.Variable.Class */
.highlight .vg { color: #dd7700 } /* Name.Variable.Global */
.highlight .vi { color: #3333bb } /* Name.Variable.Instance */
.highlight .vm { color: #336699 } /* Name.Variable.Magic */
.highlight .il { color: #0000DD; font-weight: bold } /* Literal.Number.Integer.Long */using System;
using System.Collections;
using System.Collections.Generic;
using System.Collections.ObjectModel;
using System.Diagnostics;
using System.IO;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Data;
using System.Windows.Documents;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Imaging;
using System.Windows.Navigation;
using System.Windows.Shapes;
using Tango.Core.IO;
namespace Tango.FileSystem
{
public class FileExplorerControl : Control
{
private ListBox _listBox;
private DataGrid _datagrid;
private bool _preventSynchronization;
private Point _dragOutStartPoint;
private bool _isMouseDown;
private List<FileSystemItem> _selectedItemsBeforeDrag;
public IFileSystemContainer CurrentItem
{
get { return (IFileSystemContainer)GetValue(CurrentItemProperty); }
set { SetValue(CurrentItemProperty, value); }
}
public static readonly DependencyProperty CurrentItemProperty =
DependencyProperty.Register("CurrentItem", typeof(IFileSystemContainer), typeof(FileExplorerControl), new PropertyMetadata(null));
public FileSystemItem SelectedItem
{
get { return (FileSystemItem)GetValue(SelectedItemProperty); }
set { SetValue(SelectedItemProperty, value); }
}
public static readonly DependencyProperty SelectedItemProperty =
DependencyProperty.Register("SelectedItem", typeof(FileSystemItem), typeof(FileExplorerControl), new PropertyMetadata(null));
public ICommand ItemDoubleClickedCommand
{
get { return (ICommand)GetValue(ItemDoubleClickedCommandProperty); }
set { SetValue(ItemDoubleClickedCommandProperty, value); }
}
public static readonly DependencyProperty ItemDoubleClickedCommandProperty =
DependencyProperty.Register("ItemDoubleClickedCommand", typeof(ICommand), typeof(FileExplorerControl), new PropertyMetadata(null));
public ICommand DeleteCommand
{
get { return (ICommand)GetValue(DeleteCommandProperty); }
set { SetValue(DeleteCommandProperty, value); }
}
public static readonly DependencyProperty DeleteCommandProperty =
DependencyProperty.Register("DeleteCommand", typeof(ICommand), typeof(FileExplorerControl), new PropertyMetadata(null));
public ICommand DropCommand
{
get { return (ICommand)GetValue(DropCommandProperty); }
set { SetValue(DropCommandProperty, value); }
}
public static readonly DependencyProperty DropCommandProperty =
DependencyProperty.Register("DropCommand", typeof(ICommand), typeof(FileExplorerControl), new PropertyMetadata(null));
public ICommand DragCommand
{
get { return (ICommand)GetValue(DragCommandProperty); }
set { SetValue(DragCommandProperty, value); }
}
public static readonly DependencyProperty DragCommandProperty =
DependencyProperty.Register("DragCommand", typeof(ICommand), typeof(FileExplorerControl), new PropertyMetadata(null));
public ImageSource DriveIcon
{
get { return (ImageSource)GetValue(DriveIconProperty); }
set { SetValue(DriveIconProperty, value); }
}
public static readonly DependencyProperty DriveIconProperty =
DependencyProperty.Register("DriveIcon", typeof(ImageSource), typeof(FileExplorerControl), new PropertyMetadata(null));
public ImageSource FolderIcon
{
get { return (ImageSource)GetValue(FolderIconProperty); }
set { SetValue(FolderIconProperty, value); }
}
public static readonly DependencyProperty FolderIconProperty =
DependencyProperty.Register("FolderIcon", typeof(ImageSource), typeof(FileExplorerControl), new PropertyMetadata(null));
public FileExplorerControlMode Mode
{
get { return (FileExplorerControlMode)GetValue(ModeProperty); }
set { SetValue(ModeProperty, value); }
}
public static readonly DependencyProperty ModeProperty =
DependencyProperty.Register("Mode", typeof(FileExplorerControlMode), typeof(FileExplorerControl), new PropertyMetadata(FileExplorerControlMode.Large));
public ObservableCollection<FileSystemItem> SelectedItems
{
get { return (ObservableCollection<FileSystemItem>)GetValue(SelectedItemsProperty); }
set { SetValue(SelectedItemsProperty, value); }
}
public static readonly DependencyProperty SelectedItemsProperty =
DependencyProperty.Register("SelectedItems", typeof(ObservableCollection<FileSystemItem>), typeof(FileExplorerControl), new PropertyMetadata(null, (d, e) => (d as FileExplorerControl).OnSelectedItemsChanged()));
public bool AllowDrag
{
get { return (bool)GetValue(AllowDragProperty); }
set { SetValue(AllowDragProperty, value); }
}
public static readonly DependencyProperty AllowDragProperty =
DependencyProperty.Register("AllowDrag", typeof(bool), typeof(FileExplorerControl), new PropertyMetadata(null));
static FileExplorerControl()
{
DefaultStyleKeyProperty.OverrideMetadata(typeof(FileExplorerControl), new FrameworkPropertyMetadata(typeof(FileExplorerControl)));
}
public FileExplorerControl()
{
_selectedItemsBeforeDrag = new List<FileSystemItem>();
}
public override void OnApplyTemplate()
{
base.OnApplyTemplate();
_listBox = GetTemplateChild("PART_listbox") as ListBox;
_datagrid = GetTemplateChild("PART_datagrid") as DataGrid;
_listBox.SelectionChanged += _listBox_SelectionChanged;
_datagrid.SelectionChanged += _datagrid_SelectionChanged;
}
protected override void OnPreviewKeyUp(KeyEventArgs e)
{
base.OnPreviewKeyUp(e);
if (e.Key == Key.Delete)
{
if (SelectedItems != null && SelectedItems.Count > 0)
{
DeleteCommand?.Execute(SelectedItems);
}
}
}
private void _datagrid_SelectionChanged(object sender, SelectionChangedEventArgs e)
{
if (!_preventSynchronization)
{
_preventSynchronization = true;
_listBox.SelectedItems.Clear();
foreach (var item in _datagrid.SelectedItems)
{
_listBox.SelectedItems.Add(item);
}
SynchronizeSelectedItems(_listBox.SelectedItems);
_preventSynchronization = false;
}
}
private void _listBox_SelectionChanged(object sender, SelectionChangedEventArgs e)
{
if (!_preventSynchronization)
{
_preventSynchronization = true;
_datagrid.SelectedItems.Clear();
foreach (var item in _listBox.SelectedItems)
{
_datagrid.SelectedItems.Add(item);
}
SynchronizeSelectedItems(_listBox.SelectedItems);
_preventSynchronization = false;
}
}
private void SynchronizeSelectedItems(IList items)
{
if (SelectedItems == null)
{
SelectedItems = items.Cast<FileSystemItem>().ToObservableCollection();
}
else
{
SelectedItems.Clear();
foreach (var item in items.Cast<FileSystemItem>().ToList())
{
SelectedItems.Add(item);
}
}
}
private void OnSelectedItemsChanged()
{
if (SelectedItems != null)
{
SelectedItems.CollectionChanged -= SelectedItems_CollectionChanged;
SelectedItems.CollectionChanged += SelectedItems_CollectionChanged;
SynchronizeControls();
}
}
private void SelectedItems_CollectionChanged(object sender, System.Collections.Specialized.NotifyCollectionChangedEventArgs e)
{
SynchronizeControls();
}
private void SynchronizeControls()
{
if (_listBox == null) return;
if (!_preventSynchronization)
{
_preventSynchronization = true;
_listBox.SelectedItems.Clear();
_datagrid.SelectedItems.Clear();
foreach (var item in SelectedItems)
{
_listBox.SelectedItems.Add(item);
_datagrid.SelectedItems.Add(item);
}
_preventSynchronization = false;
}
}
protected override void OnDrop(DragEventArgs e)
{
base.OnDrop(e);
try
{
string[] items = (string[])e.Data.GetData(DataFormats.FileDrop, false);
if (items != null && items.Length > 0)
{
List<FileSystemItem> fItems = new List<FileSystemItem>();
foreach (var item in items)
{
if (Directory.Exists(item))
{
fItems.Add(new FolderItem() { Path = item });
}
else if (File.Exists(item))
{
fItems.Add(new FileItem() { Path = item });
}
}
if (fItems.Count > 0)
{
DropCommand?.Execute(fItems);
}
}
}
catch { } //Ignore
}
protected override void OnPreviewMouseLeftButtonDown(MouseButtonEventArgs e)
{
base.OnPreviewMouseLeftButtonDown(e);
if (!AllowDrag) return;
if (e.OriginalSource is FrameworkElement)
{
var listBoxItem = (e.OriginalSource as FrameworkElement).FindAncestor<ListBoxItem>();
var dataGridRow = (e.OriginalSource as FrameworkElement).FindAncestor<DataGridRow>();
if (listBoxItem == null && dataGridRow == null)
{
return;
}
}
_selectedItemsBeforeDrag.Clear();
_selectedItemsBeforeDrag.AddRange(SelectedItems);
_isMouseDown = true;
AllowDrop = false;
_dragOutStartPoint = e.GetPosition(null);
}
protected override void OnPreviewMouseLeftButtonUp(MouseButtonEventArgs e)
{
base.OnPreviewMouseLeftButtonUp(e);
AllowDrop = true;
_isMouseDown = false;
}
protected async override void OnPreviewMouseMove(MouseEventArgs e)
{
base.OnPreviewMouseMove(e);
if (_isMouseDown)
{
Point mpos = e.GetPosition(null);
Vector diff = this._dragOutStartPoint - mpos;
if (e.LeftButton == MouseButtonState.Pressed &&
Math.Abs(diff.X) > SystemParameters.MinimumHorizontalDragDistance ||
Math.Abs(diff.Y) > SystemParameters.MinimumVerticalDragDistance)
{
if (SelectedItems.Count == 0)
{
return;
}
SelectedItems.Clear();
foreach (var item in _selectedItemsBeforeDrag)
{
SelectedItems.Add(item);
}
List<Tuple<FileSystemItem, TemporaryFile>> dropItems = new List<Tuple<FileSystemItem, TemporaryFile>>();
foreach (var item in SelectedItems)
{
var tempFile = TemporaryManager.Default.CreateFile(".remote");
dropItems.Add(new Tuple<FileSystemItem, TemporaryFile>(item, tempFile));
}
List<DragItem> notifyItems = new List<DragItem>();
List<FileSystemWatcher> watchers = new List<FileSystemWatcher>();
FileSystemEventHandler handler = (x, args) =>
{
var detectedDropItem = dropItems.SingleOrDefault(y => y.Item2.FileName == System.IO.Path.GetFileName(args.FullPath));
Debug.WriteLine($"File Created: {args.FullPath}");
if (detectedDropItem != null)
{
try
{
detectedDropItem.Item2.Delete(); //Delete temp file.
if (File.Exists(args.FullPath))
{
File.Delete(args.FullPath); //Delete dropped fake file.
dropItems.Remove(detectedDropItem);
notifyItems.Add(new DragItem()
{
FileSystemItem = detectedDropItem.Item1,
Destination = System.IO.Path.GetDirectoryName(args.FullPath),
});
if (dropItems.Count == 0)
{
foreach (var watcher in watchers)
{
watcher.Dispose();
}
//Notify to user with all items!
Dispatcher.BeginInvoke(new Action(() =>
{
DragCommand?.Execute(notifyItems);
}));
}
}
}
catch { }
}
else
{
Debug.WriteLine($"Not Found: {args.FullPath}");
}
};
foreach (var drive in DriveInfo.GetDrives().Where(x => x.IsReady && (x.DriveType == DriveType.Fixed || x.DriveType == DriveType.Removable)))
{
FileSystemWatcher watcher = new FileSystemWatcher(drive.RootDirectory.FullName, "*.remote");
watcher.IncludeSubdirectories = true;
watcher.EnableRaisingEvents = true;
watcher.Created += handler;
watchers.Add(watcher);
}
string[] files = dropItems.Select(x => x.Item2.Path).ToArray();
var ef = DragDrop.DoDragDrop(this, new DataObject(DataFormats.FileDrop, files, false), DragDropEffects.Copy);
await Task.Delay(3000);
foreach (var watcher in watchers)
{
watcher.Dispose();
}
if (dropItems.Count > 0)
{
//Notify about problem!
}
_isMouseDown = false;
AllowDrop = true;
}
}
}
}
}