mirror of
https://github.com/icsharpcode/ILSpy.git
synced 2026-10-12 02:15:58 +00:00
Decouple AssemblyListPane from MainWindow
This commit is contained in:
@@ -281,8 +281,9 @@ namespace ICSharpCode.ILSpyX
|
||||
{
|
||||
file = Path.GetFullPath(file);
|
||||
return OpenAssembly(file, () => {
|
||||
var newAsm = new LoadedAssembly(this, file, fileLoaders: manager?.LoaderRegistry, applyWinRTProjections: ApplyWinRTProjections, useDebugSymbols: UseDebugSymbols);
|
||||
newAsm.IsAutoLoaded = isAutoLoaded;
|
||||
var newAsm = new LoadedAssembly(this, file, fileLoaders: manager?.LoaderRegistry, applyWinRTProjections: ApplyWinRTProjections, useDebugSymbols: UseDebugSymbols) {
|
||||
IsAutoLoaded = isAutoLoaded
|
||||
};
|
||||
return newAsm;
|
||||
});
|
||||
}
|
||||
|
||||
@@ -78,12 +78,12 @@ namespace ICSharpCode.ILSpy.Analyzers
|
||||
|
||||
public override bool CanExecute(object parameter)
|
||||
{
|
||||
return MainWindow.Instance.SelectedNodes.All(n => n is IMemberTreeNode);
|
||||
return MainWindow.Instance.AssemblyTreeModel.SelectedNodes.All(n => n is IMemberTreeNode);
|
||||
}
|
||||
|
||||
public override void Execute(object parameter)
|
||||
{
|
||||
foreach (var node in MainWindow.Instance.SelectedNodes.OfType<IMemberTreeNode>())
|
||||
foreach (var node in MainWindow.Instance.AssemblyTreeModel.SelectedNodes.OfType<IMemberTreeNode>())
|
||||
{
|
||||
AnalyzerTreeView.Analyze(node.Member);
|
||||
}
|
||||
|
||||
@@ -42,7 +42,8 @@ namespace ICSharpCode.ILSpy.Analyzers
|
||||
MessageBox.Show(Properties.Resources.CannotAnalyzeMissingRef, "ILSpy");
|
||||
return;
|
||||
}
|
||||
MainWindow.Instance.JumpToReference(new EntityReference(this.Member.ParentModule.MetadataFile, this.Member.MetadataToken));
|
||||
|
||||
MessageBus.Send(this, new NavigateToReferenceEventArgs(new EntityReference(this.Member.ParentModule?.MetadataFile, this.Member.MetadataToken)));
|
||||
}
|
||||
|
||||
public override bool HandleAssemblyListChanged(ICollection<LoadedAssembly> removedAssemblies, ICollection<LoadedAssembly> addedAssemblies)
|
||||
|
||||
@@ -2,7 +2,6 @@
|
||||
using System.Collections.Specialized;
|
||||
using System.Linq;
|
||||
|
||||
using ICSharpCode.ILSpy.Util;
|
||||
using ICSharpCode.ILSpyX;
|
||||
using ICSharpCode.ILSpyX.TreeView;
|
||||
|
||||
|
||||
@@ -61,7 +61,7 @@ namespace ICSharpCode.ILSpy.Analyzers
|
||||
var context = new AnalyzerContext() {
|
||||
CancellationToken = ct,
|
||||
Language = Language,
|
||||
AssemblyList = MainWindow.Instance.CurrentAssemblyList
|
||||
AssemblyList = MainWindow.Instance.AssemblyTreeModel.CurrentAssemblyList
|
||||
};
|
||||
var results = analyzer.Analyze(symbol, context).Select(SymbolTreeNodeFactory);
|
||||
if (context.SortResults)
|
||||
|
||||
@@ -18,7 +18,6 @@
|
||||
|
||||
using System.Collections.Generic;
|
||||
|
||||
using ICSharpCode.ILSpy.Util;
|
||||
using ICSharpCode.ILSpyX;
|
||||
using ICSharpCode.ILSpyX.TreeView;
|
||||
|
||||
|
||||
@@ -61,7 +61,7 @@ namespace ICSharpCode.ILSpy.Analyzers.TreeNodes
|
||||
MessageBox.Show(Properties.Resources.CannotAnalyzeMissingRef, "ILSpy");
|
||||
return;
|
||||
}
|
||||
MainWindow.Instance.JumpToReference(analyzedModule.MetadataFile);
|
||||
MessageBus.Send(this, new NavigateToReferenceEventArgs(analyzedModule.MetadataFile));
|
||||
}
|
||||
|
||||
public override IEntity Member => null;
|
||||
|
||||
@@ -0,0 +1,54 @@
|
||||
<treeView:SharpTreeView x:Class="ICSharpCode.ILSpy.AssemblyTree.AssemblyListPane"
|
||||
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
|
||||
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
|
||||
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
|
||||
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
|
||||
xmlns:treeView="clr-namespace:ICSharpCode.ILSpy.Controls.TreeView"
|
||||
xmlns:treeNodes="clr-namespace:ICSharpCode.ILSpy.TreeNodes"
|
||||
xmlns:assemblyTree="clr-namespace:ICSharpCode.ILSpy.AssemblyTree"
|
||||
xmlns:toms="urn:TomsToolbox"
|
||||
mc:Ignorable="d" d:DesignHeight="450" d:DesignWidth="800"
|
||||
d:DataContext="{d:DesignInstance assemblyTree:AssemblyListPaneModel}"
|
||||
AutomationProperties.Name="Assemblies and Classes"
|
||||
ShowRoot="False"
|
||||
AllowDropOrder="True"
|
||||
AllowDrop="True"
|
||||
BorderThickness="0" Visibility="Visible"
|
||||
Root="{Binding Root}"
|
||||
SelectedItem="{Binding SelectedItem, Mode=TwoWay}"
|
||||
toms:MultiSelectorExtensions.SelectionBinding="{Binding SelectedItems}">
|
||||
<treeView:SharpTreeView.ItemContainerStyle>
|
||||
<Style TargetType="treeView:SharpTreeViewItem">
|
||||
<Setter Property="Template">
|
||||
<Setter.Value>
|
||||
<ControlTemplate TargetType="{x:Type treeView:SharpTreeViewItem}"
|
||||
d:DataContext="{d:DesignInstance treeNodes:ILSpyTreeNode}">
|
||||
<Border Background="Transparent">
|
||||
<Border Background="{TemplateBinding Background}">
|
||||
<treeView:SharpTreeNodeView x:Name="nodeView" HorizontalAlignment="Left" />
|
||||
</Border>
|
||||
</Border>
|
||||
<ControlTemplate.Triggers>
|
||||
<DataTrigger Binding="{Binding IsAutoLoaded}" Value="True">
|
||||
<Setter Property="Foreground" Value="SteelBlue" />
|
||||
</DataTrigger>
|
||||
<DataTrigger Binding="{Binding IsPublicAPI}" Value="False">
|
||||
<Setter Property="Foreground" Value="{DynamicResource {x:Static SystemColors.GrayTextBrushKey}}" />
|
||||
</DataTrigger>
|
||||
<Trigger Property="IsSelected" Value="True">
|
||||
<Setter TargetName="nodeView" Property="TextBackground"
|
||||
Value="{DynamicResource {x:Static SystemColors.HighlightBrushKey}}" />
|
||||
<Setter TargetName="nodeView" Property="Foreground"
|
||||
Value="{DynamicResource {x:Static SystemColors.HighlightTextBrushKey}}" />
|
||||
</Trigger>
|
||||
<Trigger Property="IsEnabled" Value="False">
|
||||
<Setter TargetName="nodeView" Property="Foreground"
|
||||
Value="{DynamicResource {x:Static SystemColors.GrayTextBrushKey}}" />
|
||||
</Trigger>
|
||||
</ControlTemplate.Triggers>
|
||||
</ControlTemplate>
|
||||
</Setter.Value>
|
||||
</Setter>
|
||||
</Style>
|
||||
</treeView:SharpTreeView.ItemContainerStyle>
|
||||
</treeView:SharpTreeView>
|
||||
@@ -0,0 +1,44 @@
|
||||
using System.ComponentModel.Composition;
|
||||
using System.Windows;
|
||||
|
||||
using ICSharpCode.ILSpyX.TreeView;
|
||||
|
||||
using TomsToolbox.Wpf.Composition.Mef;
|
||||
|
||||
namespace ICSharpCode.ILSpy.AssemblyTree
|
||||
{
|
||||
/// <summary>
|
||||
/// Interaction logic for AssemblyListPane.xaml
|
||||
/// </summary>
|
||||
[DataTemplate(typeof(AssemblyListPaneModel))]
|
||||
[PartCreationPolicy(CreationPolicy.NonShared)]
|
||||
public partial class AssemblyListPane
|
||||
{
|
||||
public AssemblyListPane()
|
||||
{
|
||||
InitializeComponent();
|
||||
|
||||
ContextMenuProvider.Add(this);
|
||||
}
|
||||
|
||||
protected override void OnPropertyChanged(DependencyPropertyChangedEventArgs e)
|
||||
{
|
||||
base.OnPropertyChanged(e);
|
||||
|
||||
if (e.Property == DataContextProperty)
|
||||
{
|
||||
if (e.NewValue is not AssemblyListPaneModel model)
|
||||
return;
|
||||
|
||||
model.SetActiveView(this);
|
||||
}
|
||||
else if (e.Property == SelectedItemProperty)
|
||||
{
|
||||
if (e.NewValue is not SharpTreeNode treeNode)
|
||||
return;
|
||||
|
||||
FocusNode(treeNode);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,896 @@
|
||||
// Copyright (c) 2019 AlphaSierraPapa for the SharpDevelop Team
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a copy of this
|
||||
// software and associated documentation files (the "Software"), to deal in the Software
|
||||
// without restriction, including without limitation the rights to use, copy, modify, merge,
|
||||
// publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons
|
||||
// to whom the Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in all copies or
|
||||
// substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED,
|
||||
// INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
|
||||
// PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE
|
||||
// FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR
|
||||
// OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
|
||||
using System.Collections.Generic;
|
||||
using System;
|
||||
using System.Collections.ObjectModel;
|
||||
using System.ComponentModel.Composition;
|
||||
using System.IO;
|
||||
using System.Threading.Tasks;
|
||||
using System.Windows.Input;
|
||||
using System.Windows.Threading;
|
||||
|
||||
using ICSharpCode.Decompiler.TypeSystem;
|
||||
using ICSharpCode.ILSpy.Docking;
|
||||
using ICSharpCode.ILSpy.Properties;
|
||||
using ICSharpCode.ILSpy.TextView;
|
||||
using ICSharpCode.ILSpy.TreeNodes;
|
||||
using ICSharpCode.ILSpy.ViewModels;
|
||||
using ICSharpCode.ILSpyX;
|
||||
using ICSharpCode.ILSpyX.Settings;
|
||||
using ICSharpCode.ILSpyX.TreeView;
|
||||
using System.Collections.Specialized;
|
||||
using System.ComponentModel;
|
||||
using System.Diagnostics;
|
||||
using System.Linq;
|
||||
using ICSharpCode.Decompiler.Metadata;
|
||||
|
||||
using System.Reflection.Metadata.Ecma335;
|
||||
using System.Windows;
|
||||
using ICSharpCode.Decompiler.Documentation;
|
||||
using ICSharpCode.Decompiler.TypeSystem.Implementation;
|
||||
using System.Reflection.Metadata;
|
||||
|
||||
using ICSharpCode.ILSpyX.Extensions;
|
||||
using ICSharpCode.ILSpy.AppEnv;
|
||||
using ICSharpCode.ILSpy.Search;
|
||||
using ICSharpCode.Decompiler;
|
||||
using System.Text;
|
||||
|
||||
using TomsToolbox.Wpf;
|
||||
|
||||
namespace ICSharpCode.ILSpy.AssemblyTree
|
||||
{
|
||||
[ExportToolPane]
|
||||
[PartCreationPolicy(CreationPolicy.Shared)]
|
||||
[Export]
|
||||
public class AssemblyListPaneModel : ToolPaneModel
|
||||
{
|
||||
public const string PaneContentId = "assemblyListPane";
|
||||
|
||||
AssemblyListPane activeView;
|
||||
AssemblyList assemblyList;
|
||||
AssemblyListTreeNode assemblyListTreeNode;
|
||||
|
||||
bool refreshInProgress;
|
||||
bool changingActiveTab;
|
||||
|
||||
readonly NavigationHistoryService history = NavigationHistoryService.Instance;
|
||||
|
||||
public AssemblyListPaneModel()
|
||||
{
|
||||
Title = Resources.Assemblies;
|
||||
ContentId = PaneContentId;
|
||||
IsCloseable = false;
|
||||
ShortcutKey = new KeyGesture(Key.F6);
|
||||
|
||||
MessageBus<NavigateToReferenceEventArgs>.Subscribers += JumpToReference;
|
||||
MessageBus<SessionSettingsChangedEventArgs>.Subscribers += (sender, e) => SessionSettings_PropertyChanged(sender, e);
|
||||
MessageBus<LanguageSettingsChangedEventArgs>.Subscribers += (sender, e) => LanguageSettings_PropertyChanged(sender, e);
|
||||
|
||||
var selectionChangeThrottle = new DispatcherThrottle(DispatcherPriority.Background, TreeView_SelectionChanged);
|
||||
SelectedItems.CollectionChanged += (_, _) => selectionChangeThrottle.Tick();
|
||||
}
|
||||
|
||||
private void SessionSettings_PropertyChanged(object sender, PropertyChangedEventArgs e)
|
||||
{
|
||||
var sessionSettings = SettingsService.Instance.SessionSettings;
|
||||
|
||||
switch (e.PropertyName)
|
||||
{
|
||||
case nameof(SessionSettings.ActiveAssemblyList):
|
||||
ShowAssemblyList(sessionSettings.ActiveAssemblyList);
|
||||
break;
|
||||
case nameof(SessionSettings.Theme):
|
||||
// update syntax highlighting and force reload (AvalonEdit does not automatically refresh on highlighting change)
|
||||
DecompilerTextView.RegisterHighlighting();
|
||||
DecompileSelectedNodes(DockWorkspace.Instance.ActiveTabPage.GetState() as DecompilerTextViewState);
|
||||
break;
|
||||
case nameof(SessionSettings.CurrentCulture):
|
||||
MessageBox.Show(Properties.Resources.SettingsChangeRestartRequired, "ILSpy");
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
public AssemblyList CurrentAssemblyList {
|
||||
get { return assemblyList; }
|
||||
}
|
||||
|
||||
private SharpTreeNode root;
|
||||
public SharpTreeNode Root {
|
||||
get => root;
|
||||
set => SetProperty(ref root, value);
|
||||
}
|
||||
|
||||
private SharpTreeNode selectedItem;
|
||||
public SharpTreeNode SelectedItem {
|
||||
get => selectedItem;
|
||||
set => SetProperty(ref selectedItem, value);
|
||||
}
|
||||
|
||||
public ObservableCollection<SharpTreeNode> SelectedItems { get; } = [];
|
||||
|
||||
public string[] SelectedPath => GetPathForNode(SelectedItem);
|
||||
|
||||
readonly List<LoadedAssembly> commandLineLoadedAssemblies = [];
|
||||
|
||||
public bool HandleCommandLineArguments(CommandLineArguments args)
|
||||
{
|
||||
LoadAssemblies(args.AssembliesToLoad, commandLineLoadedAssemblies, focusNode: false);
|
||||
if (args.Language != null)
|
||||
SettingsService.Instance.SessionSettings.LanguageSettings.Language = Languages.GetLanguage(args.Language);
|
||||
return true;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Called on startup or when passed arguments via WndProc from a second instance.
|
||||
/// In the format case, spySettings is non-null; in the latter it is null.
|
||||
/// </summary>
|
||||
public void HandleCommandLineArgumentsAfterShowList(CommandLineArguments args, ILSpySettings spySettings = null)
|
||||
{
|
||||
var sessionSettings = SettingsService.Instance.SessionSettings;
|
||||
|
||||
var relevantAssemblies = commandLineLoadedAssemblies.ToList();
|
||||
commandLineLoadedAssemblies.Clear(); // clear references once we don't need them anymore
|
||||
NavigateOnLaunch(args.NavigateTo, sessionSettings.ActiveTreeViewPath, spySettings, relevantAssemblies);
|
||||
if (args.Search != null)
|
||||
{
|
||||
var searchPane = App.ExportProvider.GetExportedValue<SearchPaneModel>();
|
||||
|
||||
searchPane.SearchTerm = args.Search;
|
||||
searchPane.Show();
|
||||
}
|
||||
}
|
||||
|
||||
public async void NavigateOnLaunch(string navigateTo, string[] activeTreeViewPath, ILSpySettings spySettings, List<LoadedAssembly> relevantAssemblies)
|
||||
{
|
||||
var initialSelection = SelectedItem;
|
||||
if (navigateTo != null)
|
||||
{
|
||||
bool found = false;
|
||||
if (navigateTo.StartsWith("N:", StringComparison.Ordinal))
|
||||
{
|
||||
string namespaceName = navigateTo.Substring(2);
|
||||
foreach (LoadedAssembly asm in relevantAssemblies)
|
||||
{
|
||||
AssemblyTreeNode asmNode = assemblyListTreeNode.FindAssemblyNode(asm);
|
||||
if (asmNode != null)
|
||||
{
|
||||
// FindNamespaceNode() blocks the UI if the assembly is not yet loaded,
|
||||
// so use an async wait instead.
|
||||
await asm.GetMetadataFileAsync().Catch<Exception>(ex => { });
|
||||
NamespaceTreeNode nsNode = asmNode.FindNamespaceNode(namespaceName);
|
||||
if (nsNode != null)
|
||||
{
|
||||
found = true;
|
||||
if (SelectedItem == initialSelection)
|
||||
{
|
||||
SelectNode(nsNode);
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
else if (navigateTo == "none")
|
||||
{
|
||||
// Don't navigate anywhere; start empty.
|
||||
// Used by ILSpy VS addin, it'll send us the real location to navigate to via IPC.
|
||||
found = true;
|
||||
}
|
||||
else
|
||||
{
|
||||
IEntity mr = await Task.Run(() => FindEntityInRelevantAssemblies(navigateTo, relevantAssemblies));
|
||||
// Make sure we wait for assemblies being loaded...
|
||||
// BeginInvoke in LoadedAssembly.LookupReferencedAssemblyInternal
|
||||
await Dispatcher.InvokeAsync(delegate { }, DispatcherPriority.Normal);
|
||||
if (mr != null && mr.ParentModule?.MetadataFile != null)
|
||||
{
|
||||
found = true;
|
||||
if (SelectedItem == initialSelection)
|
||||
{
|
||||
await JumpToReferenceAsync(mr);
|
||||
}
|
||||
}
|
||||
}
|
||||
if (!found && SelectedItem == initialSelection)
|
||||
{
|
||||
AvalonEditTextOutput output = new AvalonEditTextOutput();
|
||||
output.Write($"Cannot find '{navigateTo}' in command line specified assemblies.");
|
||||
DockWorkspace.Instance.ShowText(output);
|
||||
}
|
||||
}
|
||||
else if (relevantAssemblies.Count == 1)
|
||||
{
|
||||
// NavigateTo == null and an assembly was given on the command-line:
|
||||
// Select the newly loaded assembly
|
||||
AssemblyTreeNode asmNode = assemblyListTreeNode.FindAssemblyNode(relevantAssemblies[0]);
|
||||
if (asmNode != null && SelectedItem == initialSelection)
|
||||
{
|
||||
SelectNode(asmNode);
|
||||
}
|
||||
}
|
||||
else if (spySettings != null)
|
||||
{
|
||||
SharpTreeNode node = null;
|
||||
if (activeTreeViewPath?.Length > 0)
|
||||
{
|
||||
foreach (var asm in CurrentAssemblyList.GetAssemblies())
|
||||
{
|
||||
if (asm.FileName == activeTreeViewPath[0])
|
||||
{
|
||||
// FindNodeByPath() blocks the UI if the assembly is not yet loaded,
|
||||
// so use an async wait instead.
|
||||
await asm.GetMetadataFileAsync().Catch<Exception>(ex => { });
|
||||
}
|
||||
}
|
||||
node = FindNodeByPath(activeTreeViewPath, true);
|
||||
}
|
||||
if (SelectedItem == initialSelection)
|
||||
{
|
||||
if (node != null)
|
||||
{
|
||||
SelectNode(node);
|
||||
|
||||
// only if not showing the about page, perform the update check:
|
||||
await MainWindow.Instance.ShowMessageIfUpdatesAvailableAsync(spySettings);
|
||||
}
|
||||
else
|
||||
{
|
||||
DockWorkspace.Instance.ActiveTabPage.ShowTextView(AboutPage.Display);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public static IEntity FindEntityInRelevantAssemblies(string navigateTo, IEnumerable<LoadedAssembly> relevantAssemblies)
|
||||
{
|
||||
ITypeReference typeRef;
|
||||
IMemberReference memberRef = null;
|
||||
if (navigateTo.StartsWith("T:", StringComparison.Ordinal))
|
||||
{
|
||||
typeRef = IdStringProvider.ParseTypeName(navigateTo);
|
||||
}
|
||||
else
|
||||
{
|
||||
memberRef = IdStringProvider.ParseMemberIdString(navigateTo);
|
||||
typeRef = memberRef.DeclaringTypeReference;
|
||||
}
|
||||
foreach (LoadedAssembly asm in relevantAssemblies.ToList())
|
||||
{
|
||||
var module = asm.GetMetadataFileOrNull();
|
||||
if (CanResolveTypeInPEFile(module, typeRef, out var typeHandle))
|
||||
{
|
||||
ICompilation compilation = typeHandle.Kind == HandleKind.ExportedType
|
||||
? new DecompilerTypeSystem(module, module.GetAssemblyResolver())
|
||||
: new SimpleCompilation((PEFile)module, MinimalCorlib.Instance);
|
||||
return memberRef == null
|
||||
? typeRef.Resolve(new SimpleTypeResolveContext(compilation)) as ITypeDefinition
|
||||
: memberRef.Resolve(new SimpleTypeResolveContext(compilation));
|
||||
}
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
static bool CanResolveTypeInPEFile(MetadataFile module, ITypeReference typeRef, out EntityHandle typeHandle)
|
||||
{
|
||||
// We intentionally ignore reference assemblies, so that the loop continues looking for another assembly that might have a usable definition.
|
||||
if (module.IsReferenceAssembly())
|
||||
{
|
||||
typeHandle = default;
|
||||
return false;
|
||||
}
|
||||
|
||||
switch (typeRef)
|
||||
{
|
||||
case GetPotentiallyNestedClassTypeReference topLevelType:
|
||||
typeHandle = topLevelType.ResolveInPEFile(module);
|
||||
return !typeHandle.IsNil;
|
||||
case NestedTypeReference nestedType:
|
||||
if (!CanResolveTypeInPEFile(module, nestedType.DeclaringTypeReference, out typeHandle))
|
||||
return false;
|
||||
if (typeHandle.Kind == HandleKind.ExportedType)
|
||||
return true;
|
||||
var typeDef = module.Metadata.GetTypeDefinition((TypeDefinitionHandle)typeHandle);
|
||||
typeHandle = typeDef.GetNestedTypes().FirstOrDefault(t => {
|
||||
var td = module.Metadata.GetTypeDefinition(t);
|
||||
var typeName = ReflectionHelper.SplitTypeParameterCountFromReflectionName(module.Metadata.GetString(td.Name), out int typeParameterCount);
|
||||
return nestedType.AdditionalTypeParameterCount == typeParameterCount && nestedType.Name == typeName;
|
||||
});
|
||||
return !typeHandle.IsNil;
|
||||
default:
|
||||
typeHandle = default;
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
public void Initialize()
|
||||
{
|
||||
var loadPreviousAssemblies = Options.MiscSettingsPanel.CurrentMiscSettings.LoadPreviousAssemblies;
|
||||
|
||||
var sessionSettings = SettingsService.Instance.SessionSettings;
|
||||
|
||||
if (loadPreviousAssemblies)
|
||||
{
|
||||
this.assemblyList = SettingsService.Instance.AssemblyListManager.LoadList(sessionSettings.ActiveAssemblyList);
|
||||
}
|
||||
else
|
||||
{
|
||||
SettingsService.Instance.AssemblyListManager.ClearAll();
|
||||
this.assemblyList = SettingsService.Instance.AssemblyListManager.CreateList(AssemblyListManager.DefaultListName);
|
||||
}
|
||||
|
||||
HandleCommandLineArguments(App.CommandLineArguments);
|
||||
|
||||
if (assemblyList.GetAssemblies().Length == 0
|
||||
&& assemblyList.ListName == AssemblyListManager.DefaultListName
|
||||
&& loadPreviousAssemblies)
|
||||
{
|
||||
LoadInitialAssemblies();
|
||||
}
|
||||
|
||||
ShowAssemblyList(this.assemblyList);
|
||||
|
||||
if (sessionSettings.ActiveAutoLoadedAssembly != null
|
||||
&& File.Exists(sessionSettings.ActiveAutoLoadedAssembly))
|
||||
{
|
||||
this.assemblyList.Open(sessionSettings.ActiveAutoLoadedAssembly, true);
|
||||
}
|
||||
|
||||
Dispatcher.BeginInvoke(DispatcherPriority.Loaded, new Action(() => OpenAssemblies(SettingsService.Instance.SpySettings)));
|
||||
}
|
||||
|
||||
void OpenAssemblies(ILSpySettings spySettings)
|
||||
{
|
||||
HandleCommandLineArgumentsAfterShowList(App.CommandLineArguments, spySettings);
|
||||
|
||||
AvalonEditTextOutput output = new();
|
||||
if (FormatExceptions(App.StartupExceptions.ToArray(), output))
|
||||
DockWorkspace.Instance.ShowText(output);
|
||||
}
|
||||
|
||||
static bool FormatExceptions(App.ExceptionData[] exceptions, ITextOutput output)
|
||||
{
|
||||
var stringBuilder = new StringBuilder();
|
||||
var result = exceptions.FormatExceptions(stringBuilder);
|
||||
if (result)
|
||||
{
|
||||
output.Write(stringBuilder.ToString());
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
public void ShowAssemblyList(string name)
|
||||
{
|
||||
AssemblyList list = SettingsService.Instance.AssemblyListManager.LoadList(name);
|
||||
//Only load a new list when it is a different one
|
||||
if (list.ListName != CurrentAssemblyList.ListName)
|
||||
{
|
||||
ShowAssemblyList(list);
|
||||
SelectNode(Root);
|
||||
}
|
||||
}
|
||||
|
||||
void ShowAssemblyList(AssemblyList assemblyList)
|
||||
{
|
||||
history.Clear();
|
||||
if (this.assemblyList != null)
|
||||
{
|
||||
this.assemblyList.CollectionChanged -= assemblyList_CollectionChanged;
|
||||
}
|
||||
|
||||
this.assemblyList = assemblyList;
|
||||
|
||||
assemblyList.CollectionChanged += assemblyList_CollectionChanged;
|
||||
|
||||
assemblyListTreeNode = new(assemblyList) {
|
||||
Select = x => SelectNode(x)
|
||||
};
|
||||
|
||||
Root = assemblyListTreeNode;
|
||||
|
||||
if (assemblyList.ListName == AssemblyListManager.DefaultListName)
|
||||
#if DEBUG
|
||||
this.Title = $"ILSpy {DecompilerVersionInfo.FullVersion}";
|
||||
#else
|
||||
this.Title = "ILSpy";
|
||||
#endif
|
||||
else
|
||||
#if DEBUG
|
||||
this.Title = $"ILSpy {DecompilerVersionInfo.FullVersion} - " + assemblyList.ListName;
|
||||
#else
|
||||
this.Title = "ILSpy - " + assemblyList.ListName;
|
||||
#endif
|
||||
}
|
||||
|
||||
void assemblyList_CollectionChanged(object sender, NotifyCollectionChangedEventArgs e)
|
||||
{
|
||||
if (e.Action == NotifyCollectionChangedAction.Reset)
|
||||
{
|
||||
history.RemoveAll(_ => true);
|
||||
}
|
||||
if (e.OldItems != null)
|
||||
{
|
||||
var oldAssemblies = new HashSet<LoadedAssembly>(e.OldItems.Cast<LoadedAssembly>());
|
||||
history.RemoveAll(n => n.TreeNodes.Any(
|
||||
nd => nd.AncestorsAndSelf().OfType<AssemblyTreeNode>().Any(
|
||||
a => oldAssemblies.Contains(a.LoadedAssembly))));
|
||||
}
|
||||
|
||||
MessageBus.Send(this, new CurrentAssemblyListChangedEventArgs(e));
|
||||
}
|
||||
|
||||
void LoadInitialAssemblies()
|
||||
{
|
||||
// Called when loading an empty assembly list; so that
|
||||
// the user can see something initially.
|
||||
System.Reflection.Assembly[] initialAssemblies = {
|
||||
typeof(object).Assembly,
|
||||
typeof(Uri).Assembly,
|
||||
typeof(System.Linq.Enumerable).Assembly,
|
||||
typeof(System.Xml.XmlDocument).Assembly,
|
||||
typeof(System.Windows.Markup.MarkupExtension).Assembly,
|
||||
typeof(System.Windows.Rect).Assembly,
|
||||
typeof(System.Windows.UIElement).Assembly,
|
||||
typeof(System.Windows.FrameworkElement).Assembly
|
||||
};
|
||||
foreach (System.Reflection.Assembly asm in initialAssemblies)
|
||||
assemblyList.OpenAssembly(asm.Location);
|
||||
}
|
||||
|
||||
void LanguageSettings_PropertyChanged(object sender, PropertyChangedEventArgs e)
|
||||
{
|
||||
if (e.PropertyName == "Language" || e.PropertyName == "LanguageVersion")
|
||||
{
|
||||
DecompileSelectedNodes(recordHistory: false);
|
||||
}
|
||||
}
|
||||
|
||||
public AssemblyTreeNode FindAssemblyNode(LoadedAssembly asm)
|
||||
{
|
||||
return assemblyListTreeNode.FindAssemblyNode(asm);
|
||||
}
|
||||
|
||||
#region Node Selection
|
||||
|
||||
public void SelectNode(SharpTreeNode node, bool inNewTabPage = false)
|
||||
{
|
||||
if (node == null)
|
||||
return;
|
||||
|
||||
if (node.AncestorsAndSelf().Any(item => item.IsHidden))
|
||||
{
|
||||
MessageBox.Show(Properties.Resources.NavigationFailed, "ILSpy", MessageBoxButton.OK, MessageBoxImage.Exclamation);
|
||||
return;
|
||||
}
|
||||
|
||||
if (inNewTabPage)
|
||||
{
|
||||
DockWorkspace.Instance.TabPages.Add();
|
||||
SelectedItem = null;
|
||||
}
|
||||
|
||||
if (SelectedItem == node)
|
||||
{
|
||||
Dispatcher.BeginInvoke(RefreshDecompiledView);
|
||||
}
|
||||
else
|
||||
{
|
||||
activeView?.ScrollIntoView(node);
|
||||
SelectedItem = node;
|
||||
}
|
||||
}
|
||||
|
||||
internal void SelectNodes(IEnumerable<SharpTreeNode> nodes, bool inNewTabPage = false, bool setFocus = true, bool changingTab = false, bool ignoreCompilationRequests = false)
|
||||
{
|
||||
this.ignoreDecompilationRequests = ignoreCompilationRequests;
|
||||
|
||||
try
|
||||
{
|
||||
|
||||
if (inNewTabPage)
|
||||
{
|
||||
DockWorkspace.Instance.TabPages.Add();
|
||||
}
|
||||
|
||||
// Ensure nodes exist
|
||||
var nodesList = nodes.Select(n => FindNodeByPath(GetPathForNode(n), true))
|
||||
.Where(n => n != null)
|
||||
.ToArray();
|
||||
|
||||
if (!nodesList.Any() || nodesList.Any(n => n.AncestorsAndSelf().Any(a => a.IsHidden)))
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
this.changingActiveTab = changingTab || inNewTabPage;
|
||||
|
||||
var currentFocused = Keyboard.FocusedElement;
|
||||
|
||||
try
|
||||
{
|
||||
if (SelectedItems.SequenceEqual(nodesList))
|
||||
{
|
||||
Dispatcher.BeginInvoke(RefreshDecompiledView);
|
||||
return;
|
||||
}
|
||||
|
||||
this.SelectedItems.Clear();
|
||||
this.SelectedItems.AddRange(nodesList);
|
||||
}
|
||||
finally
|
||||
{
|
||||
if (!setFocus)
|
||||
currentFocused.Focus();
|
||||
|
||||
this.changingActiveTab = false;
|
||||
}
|
||||
}
|
||||
finally
|
||||
{
|
||||
this.ignoreDecompilationRequests = false;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Retrieves a node using the .ToString() representations of its ancestors.
|
||||
/// </summary>
|
||||
public SharpTreeNode FindNodeByPath(string[] path, bool returnBestMatch)
|
||||
{
|
||||
if (path == null)
|
||||
return null;
|
||||
SharpTreeNode node = Root;
|
||||
SharpTreeNode bestMatch = node;
|
||||
foreach (var element in path)
|
||||
{
|
||||
if (node == null)
|
||||
break;
|
||||
bestMatch = node;
|
||||
node.EnsureLazyChildren();
|
||||
if (node is ILSpyTreeNode ilSpyTreeNode)
|
||||
ilSpyTreeNode.EnsureChildrenFiltered();
|
||||
node = node.Children.FirstOrDefault(c => c.ToString() == element);
|
||||
}
|
||||
if (returnBestMatch)
|
||||
return node ?? bestMatch;
|
||||
else
|
||||
return node;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the .ToString() representation of the node's ancestors.
|
||||
/// </summary>
|
||||
public static string[] GetPathForNode(SharpTreeNode node)
|
||||
{
|
||||
if (node == null)
|
||||
return null;
|
||||
List<string> path = new List<string>();
|
||||
while (node.Parent != null)
|
||||
{
|
||||
path.Add(node.ToString());
|
||||
node = node.Parent;
|
||||
}
|
||||
path.Reverse();
|
||||
return path.ToArray();
|
||||
}
|
||||
|
||||
public ILSpyTreeNode FindTreeNode(object reference)
|
||||
{
|
||||
switch (reference)
|
||||
{
|
||||
case LoadedAssembly lasm:
|
||||
return assemblyListTreeNode.FindAssemblyNode(lasm);
|
||||
case MetadataFile asm:
|
||||
return assemblyListTreeNode.FindAssemblyNode(asm);
|
||||
case Resource res:
|
||||
return assemblyListTreeNode.FindResourceNode(res);
|
||||
case ValueTuple<Resource, string> resName:
|
||||
return assemblyListTreeNode.FindResourceNode(resName.Item1, resName.Item2);
|
||||
case ITypeDefinition type:
|
||||
return assemblyListTreeNode.FindTypeNode(type);
|
||||
case IField fd:
|
||||
return assemblyListTreeNode.FindFieldNode(fd);
|
||||
case IMethod md:
|
||||
return assemblyListTreeNode.FindMethodNode(md);
|
||||
case IProperty pd:
|
||||
return assemblyListTreeNode.FindPropertyNode(pd);
|
||||
case IEvent ed:
|
||||
return assemblyListTreeNode.FindEventNode(ed);
|
||||
case INamespace nd:
|
||||
return assemblyListTreeNode.FindNamespaceNode(nd);
|
||||
default:
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
private void JumpToReference(object sender, NavigateToReferenceEventArgs e)
|
||||
{
|
||||
JumpToReferenceAsync(e.Reference, e.InNewTabPage).HandleExceptions();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Jumps to the specified reference.
|
||||
/// </summary>
|
||||
/// <returns>
|
||||
/// Returns a task that will signal completion when the decompilation of the jump target has finished.
|
||||
/// The task will be marked as canceled if the decompilation is canceled.
|
||||
/// </returns>
|
||||
private Task JumpToReferenceAsync(object reference, bool inNewTabPage = false)
|
||||
{
|
||||
var decompilationTask = Task.CompletedTask;
|
||||
|
||||
switch (reference)
|
||||
{
|
||||
case Decompiler.Disassembler.OpCodeInfo opCode:
|
||||
MainWindow.OpenLink(opCode.Link);
|
||||
break;
|
||||
case EntityReference unresolvedEntity:
|
||||
string protocol = unresolvedEntity.Protocol;
|
||||
var file = unresolvedEntity.ResolveAssembly(assemblyList);
|
||||
if (file == null)
|
||||
{
|
||||
break;
|
||||
}
|
||||
if (protocol != "decompile")
|
||||
{
|
||||
var protocolHandlers = App.ExportProvider.GetExportedValues<IProtocolHandler>();
|
||||
foreach (var handler in protocolHandlers)
|
||||
{
|
||||
var node = handler.Resolve(protocol, file, unresolvedEntity.Handle, out bool newTabPage);
|
||||
if (node != null)
|
||||
{
|
||||
SelectNode(node, newTabPage || inNewTabPage);
|
||||
return decompilationTask;
|
||||
}
|
||||
}
|
||||
}
|
||||
var possibleToken = MetadataTokenHelpers.TryAsEntityHandle(MetadataTokens.GetToken(unresolvedEntity.Handle));
|
||||
if (possibleToken != null)
|
||||
{
|
||||
var typeSystem = new DecompilerTypeSystem(file, file.GetAssemblyResolver(), TypeSystemOptions.Default | TypeSystemOptions.Uncached);
|
||||
reference = typeSystem.MainModule.ResolveEntity(possibleToken.Value);
|
||||
goto default;
|
||||
}
|
||||
break;
|
||||
default:
|
||||
ILSpyTreeNode treeNode = FindTreeNode(reference);
|
||||
if (treeNode != null)
|
||||
SelectNode(treeNode, inNewTabPage);
|
||||
break;
|
||||
}
|
||||
return decompilationTask;
|
||||
}
|
||||
|
||||
#endregion
|
||||
|
||||
public void LoadAssemblies(IEnumerable<string> fileNames, List<LoadedAssembly> loadedAssemblies = null, bool focusNode = true)
|
||||
{
|
||||
var currentFocus = Keyboard.FocusedElement;
|
||||
AssemblyTreeNode lastNode = null;
|
||||
|
||||
foreach (string file in fileNames)
|
||||
{
|
||||
var assembly = assemblyList.OpenAssembly(file);
|
||||
|
||||
if (loadedAssemblies != null)
|
||||
{
|
||||
loadedAssemblies.Add(assembly);
|
||||
}
|
||||
else
|
||||
{
|
||||
var node = assemblyListTreeNode.FindAssemblyNode(assembly);
|
||||
if (node != null && focusNode)
|
||||
{
|
||||
lastNode = node;
|
||||
SelectedItems.Add(node);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (!focusNode)
|
||||
{
|
||||
currentFocus?.Focus();
|
||||
}
|
||||
else if (lastNode != null)
|
||||
{
|
||||
activeView?.FocusNode(lastNode);
|
||||
}
|
||||
}
|
||||
|
||||
#region Decompile (TreeView_SelectionChanged)
|
||||
|
||||
void TreeView_SelectionChanged()
|
||||
{
|
||||
DecompilerTextViewState state = null;
|
||||
|
||||
// These are probably no longer needed and can be removed!
|
||||
Debug.Assert(!refreshInProgress);
|
||||
Debug.Assert(!changingActiveTab);
|
||||
|
||||
if (refreshInProgress || changingActiveTab)
|
||||
{
|
||||
state = DockWorkspace.Instance.ActiveTabPage.GetState() as DecompilerTextViewState;
|
||||
}
|
||||
|
||||
var delayDecompilationRequestDueToContextMenu = Mouse.RightButton == MouseButtonState.Pressed;
|
||||
|
||||
if (!changingActiveTab && !delayDecompilationRequestDueToContextMenu)
|
||||
{
|
||||
DecompileSelectedNodes(state);
|
||||
}
|
||||
else
|
||||
{
|
||||
ContextMenuProvider.ContextMenuClosed += ContextMenuClosed;
|
||||
}
|
||||
|
||||
MessageBus.Send(this, new AssemblyTreeSelectionChangedEventArgs());
|
||||
|
||||
return;
|
||||
|
||||
void ContextMenuClosed(object sender, EventArgs e)
|
||||
{
|
||||
ContextMenuProvider.ContextMenuClosed -= ContextMenuClosed;
|
||||
|
||||
Dispatcher.BeginInvoke(DispatcherPriority.Background, () => {
|
||||
if (Mouse.RightButton != MouseButtonState.Pressed)
|
||||
{
|
||||
DecompileSelectedNodes(DockWorkspace.Instance.ActiveTabPage.GetState() as DecompilerTextViewState);
|
||||
}
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
private bool ignoreDecompilationRequests;
|
||||
|
||||
public void DecompileSelectedNodes(DecompilerTextViewState newState = null, bool recordHistory = true)
|
||||
{
|
||||
if (ignoreDecompilationRequests)
|
||||
return;
|
||||
|
||||
if (SelectedItems.Count == 0 && refreshInProgress)
|
||||
return;
|
||||
|
||||
if (recordHistory)
|
||||
{
|
||||
var tabPage = DockWorkspace.Instance.ActiveTabPage;
|
||||
var currentState = tabPage.GetState();
|
||||
if (currentState != null)
|
||||
history.UpdateCurrent(new NavigationState(tabPage, currentState));
|
||||
history.Record(new NavigationState(tabPage, SelectedItems));
|
||||
}
|
||||
|
||||
DockWorkspace.Instance.ActiveTabPage.SupportsLanguageSwitching = true;
|
||||
|
||||
if (SelectedItems.Count == 1)
|
||||
{
|
||||
if (SelectedItem is ILSpyTreeNode node && node.View(DockWorkspace.Instance.ActiveTabPage))
|
||||
return;
|
||||
}
|
||||
if (newState?.ViewedUri != null)
|
||||
{
|
||||
MainWindow.Instance.NavigateTo(new(newState.ViewedUri, null), recordHistory: false);
|
||||
return;
|
||||
}
|
||||
var options = MainWindow.Instance.CreateDecompilationOptions();
|
||||
options.TextViewState = newState;
|
||||
DockWorkspace.Instance.ActiveTabPage.ShowTextViewAsync(textView => textView.DecompileAsync(this.CurrentLanguage, this.SelectedNodes, options));
|
||||
}
|
||||
|
||||
public void RefreshDecompiledView()
|
||||
{
|
||||
try
|
||||
{
|
||||
refreshInProgress = true;
|
||||
DecompileSelectedNodes();
|
||||
}
|
||||
finally
|
||||
{
|
||||
refreshInProgress = false;
|
||||
}
|
||||
}
|
||||
|
||||
public Language CurrentLanguage => SettingsService.Instance.SessionSettings.LanguageSettings.Language;
|
||||
|
||||
public LanguageVersion CurrentLanguageVersion => SettingsService.Instance.SessionSettings.LanguageSettings.LanguageVersion;
|
||||
|
||||
public IEnumerable<ILSpyTreeNode> SelectedNodes {
|
||||
get {
|
||||
return GetTopLevelSelection().OfType<ILSpyTreeNode>();
|
||||
}
|
||||
}
|
||||
|
||||
#endregion
|
||||
|
||||
|
||||
public void Refresh()
|
||||
{
|
||||
var currentFocus = Keyboard.FocusedElement;
|
||||
|
||||
try
|
||||
{
|
||||
refreshInProgress = true;
|
||||
var path = GetPathForNode(SelectedItem);
|
||||
ShowAssemblyList(SettingsService.Instance.AssemblyListManager.LoadList(assemblyList.ListName));
|
||||
SelectNode(FindNodeByPath(path, true), inNewTabPage: false);
|
||||
}
|
||||
finally
|
||||
{
|
||||
refreshInProgress = false;
|
||||
currentFocus?.Focus();
|
||||
}
|
||||
}
|
||||
|
||||
public void UnselectAll(bool ignoreCompilationRequests = false)
|
||||
{
|
||||
this.ignoreDecompilationRequests = ignoreCompilationRequests;
|
||||
SelectedItems.Clear();
|
||||
this.ignoreDecompilationRequests = false;
|
||||
}
|
||||
|
||||
public IEnumerable<SharpTreeNode> GetTopLevelSelection()
|
||||
{
|
||||
var selection = this.SelectedItems;
|
||||
var selectionHash = new HashSet<SharpTreeNode>(selection);
|
||||
|
||||
return selection.Where(item => item.Ancestors().All(a => !selectionHash.Contains(a)));
|
||||
}
|
||||
|
||||
public void SetActiveView(AssemblyListPane activeView)
|
||||
{
|
||||
this.activeView = activeView;
|
||||
}
|
||||
|
||||
public void SortAssemblyList()
|
||||
{
|
||||
using (activeView?.LockUpdates())
|
||||
{
|
||||
CurrentAssemblyList.Sort(AssemblyComparer.Instance);
|
||||
}
|
||||
}
|
||||
|
||||
private class AssemblyComparer : IComparer<LoadedAssembly>
|
||||
{
|
||||
public static readonly AssemblyComparer Instance = new();
|
||||
int IComparer<LoadedAssembly>.Compare(LoadedAssembly x, LoadedAssembly y)
|
||||
{
|
||||
return string.Compare(x?.ShortName, y?.ShortName, StringComparison.CurrentCulture);
|
||||
}
|
||||
}
|
||||
|
||||
public void CollapseAll()
|
||||
{
|
||||
using (activeView.LockUpdates())
|
||||
{
|
||||
CollapseChildren(Root);
|
||||
}
|
||||
}
|
||||
|
||||
static void CollapseChildren(SharpTreeNode node)
|
||||
{
|
||||
foreach (var child in node.Children)
|
||||
{
|
||||
if (!child.IsExpanded)
|
||||
continue;
|
||||
|
||||
CollapseChildren(child);
|
||||
child.IsExpanded = false;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -28,7 +28,6 @@ using System.Threading.Tasks;
|
||||
using ICSharpCode.Decompiler;
|
||||
using ICSharpCode.ILSpy.Properties;
|
||||
using ICSharpCode.ILSpy.TextView;
|
||||
using ICSharpCode.ILSpy.Util;
|
||||
using ICSharpCode.ILSpyX;
|
||||
|
||||
using TomsToolbox.Essentials;
|
||||
@@ -49,7 +48,7 @@ namespace ICSharpCode.ILSpy
|
||||
Docking.DockWorkspace.Instance.RunWithCancellation(ct => Task<AvalonEditTextOutput>.Factory.StartNew(() => {
|
||||
AvalonEditTextOutput output = new AvalonEditTextOutput();
|
||||
Parallel.ForEach(
|
||||
Partitioner.Create(MainWindow.Instance.CurrentAssemblyList.GetAssemblies(), loadBalance: true),
|
||||
Partitioner.Create(MainWindow.Instance.AssemblyTreeModel.CurrentAssemblyList.GetAssemblies(), loadBalance: true),
|
||||
new ParallelOptions { MaxDegreeOfParallelism = Environment.ProcessorCount, CancellationToken = ct },
|
||||
delegate (LoadedAssembly asm) {
|
||||
if (!asm.HasLoadError)
|
||||
@@ -96,7 +95,7 @@ namespace ICSharpCode.ILSpy
|
||||
{
|
||||
const int numRuns = 100;
|
||||
var language = SettingsService.Instance.SessionSettings.LanguageSettings.Language;
|
||||
var nodes = MainWindow.Instance.SelectedNodes.ToArray();
|
||||
var nodes = MainWindow.Instance.AssemblyTreeModel.SelectedNodes.ToArray();
|
||||
var options = MainWindow.Instance.CreateDecompilationOptions();
|
||||
Docking.DockWorkspace.Instance.RunWithCancellation(ct => Task<AvalonEditTextOutput>.Factory.StartNew(() => {
|
||||
options.CancellationToken = ct;
|
||||
|
||||
@@ -66,7 +66,7 @@ namespace ICSharpCode.ILSpy.Commands
|
||||
selection = entity;
|
||||
}
|
||||
if (selection != null)
|
||||
MainWindow.Instance.JumpToReference(selection);
|
||||
MessageBus.Send(this, new NavigateToReferenceEventArgs(selection));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -23,11 +23,11 @@ using System.Linq;
|
||||
using System.Windows.Threading;
|
||||
|
||||
using ICSharpCode.Decompiler.TypeSystem;
|
||||
using ICSharpCode.ILSpy.Docking;
|
||||
using ICSharpCode.ILSpy.Properties;
|
||||
using ICSharpCode.ILSpy.TextView;
|
||||
using ICSharpCode.ILSpy.TreeNodes;
|
||||
|
||||
using TomsToolbox.Essentials;
|
||||
|
||||
namespace ICSharpCode.ILSpy.Commands
|
||||
{
|
||||
[ExportContextMenuEntry(Header = nameof(Resources.DecompileToNewPanel), InputGestureText = "MMB", Icon = "images/Search", Category = nameof(Resources.Analyze), Order = 90)]
|
||||
@@ -53,18 +53,18 @@ namespace ICSharpCode.ILSpy.Commands
|
||||
{
|
||||
if (context.SelectedTreeNodes != null)
|
||||
{
|
||||
if (context.TreeView != MainWindow.Instance.AssemblyTreeView)
|
||||
if (context.TreeView.DataContext != MainWindow.Instance.AssemblyTreeModel)
|
||||
{
|
||||
return context.SelectedTreeNodes.OfType<IMemberTreeNode>().Select(FindTreeNode).Where(n => n != null);
|
||||
return context.SelectedTreeNodes.OfType<IMemberTreeNode>().Select(FindTreeNode).ExceptNullItems();
|
||||
}
|
||||
else
|
||||
{
|
||||
return context.SelectedTreeNodes.OfType<ILSpyTreeNode>().Where(n => n != null);
|
||||
return context.SelectedTreeNodes.OfType<ILSpyTreeNode>();
|
||||
}
|
||||
}
|
||||
else if (context.Reference?.Reference is IEntity entity)
|
||||
{
|
||||
if (MainWindow.Instance.FindTreeNode(entity) is ILSpyTreeNode node)
|
||||
if (MainWindow.Instance.AssemblyTreeModel.FindTreeNode(entity) is { } node)
|
||||
{
|
||||
return new[] { node };
|
||||
}
|
||||
@@ -75,7 +75,7 @@ namespace ICSharpCode.ILSpy.Commands
|
||||
{
|
||||
if (node is ILSpyTreeNode ilspyNode)
|
||||
return ilspyNode;
|
||||
return MainWindow.Instance.FindTreeNode(node.Member);
|
||||
return MainWindow.Instance.AssemblyTreeModel.FindTreeNode(node.Member);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -84,8 +84,7 @@ namespace ICSharpCode.ILSpy.Commands
|
||||
if (nodes.Length == 0)
|
||||
return;
|
||||
|
||||
MainWindow.Instance.SelectNodes(nodes, inNewTabPage: true);
|
||||
MainWindow.Instance.Dispatcher.BeginInvoke(DispatcherPriority.Background, (Action)MainWindow.Instance.RefreshDecompiledView);
|
||||
MainWindow.Instance.AssemblyTreeModel.SelectNodes(nodes, inNewTabPage: true);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -44,7 +44,7 @@ namespace ICSharpCode.ILSpy
|
||||
Docking.DockWorkspace.Instance.RunWithCancellation(ct => Task<AvalonEditTextOutput>.Factory.StartNew(() => {
|
||||
AvalonEditTextOutput output = new AvalonEditTextOutput();
|
||||
Parallel.ForEach(
|
||||
Partitioner.Create(MainWindow.Instance.CurrentAssemblyList.GetAssemblies(), loadBalance: true),
|
||||
Partitioner.Create(MainWindow.Instance.AssemblyTreeModel.CurrentAssemblyList.GetAssemblies(), loadBalance: true),
|
||||
new ParallelOptions { MaxDegreeOfParallelism = Environment.ProcessorCount, CancellationToken = ct },
|
||||
delegate (LoadedAssembly asm) {
|
||||
if (!asm.HasLoadError)
|
||||
|
||||
@@ -110,14 +110,14 @@ namespace ICSharpCode.ILSpy
|
||||
{
|
||||
public override bool CanExecute(object parameter)
|
||||
{
|
||||
return MainWindow.Instance.SelectedNodes?.Count() == 1
|
||||
&& MainWindow.Instance.SelectedNodes?.FirstOrDefault() is AssemblyTreeNode tn
|
||||
return MainWindow.Instance.AssemblyTreeModel.SelectedNodes?.Count() == 1
|
||||
&& MainWindow.Instance.AssemblyTreeModel.SelectedNodes?.FirstOrDefault() is AssemblyTreeNode tn
|
||||
&& !tn.LoadedAssembly.HasLoadError;
|
||||
}
|
||||
|
||||
public override void Execute(object parameter)
|
||||
{
|
||||
var assembly = (MainWindow.Instance.SelectedNodes?.FirstOrDefault() as AssemblyTreeNode)?.LoadedAssembly;
|
||||
var assembly = (MainWindow.Instance.AssemblyTreeModel.SelectedNodes?.FirstOrDefault() as AssemblyTreeNode)?.LoadedAssembly;
|
||||
if (assembly == null)
|
||||
return;
|
||||
GeneratePdbContextMenuEntry.GeneratePdbForAssembly(assembly);
|
||||
|
||||
@@ -40,14 +40,14 @@ namespace ICSharpCode.ILSpy
|
||||
{
|
||||
public override bool CanExecute(object parameter)
|
||||
{
|
||||
var selectedNodes = MainWindow.Instance.SelectedNodes;
|
||||
var selectedNodes = MainWindow.Instance.AssemblyTreeModel.SelectedNodes;
|
||||
return selectedNodes?.Any() == true
|
||||
&& selectedNodes.All(n => n is AssemblyTreeNode asm && !asm.LoadedAssembly.HasLoadError);
|
||||
}
|
||||
|
||||
public override void Execute(object parameter)
|
||||
{
|
||||
Execute(MainWindow.Instance.SelectedNodes.OfType<AssemblyTreeNode>());
|
||||
Execute(MainWindow.Instance.AssemblyTreeModel.SelectedNodes.OfType<AssemblyTreeNode>());
|
||||
}
|
||||
|
||||
internal static void Execute(IEnumerable<AssemblyTreeNode> nodes)
|
||||
|
||||
@@ -29,16 +29,16 @@ namespace ICSharpCode.ILSpy
|
||||
{
|
||||
public override bool CanExecute(object parameter)
|
||||
{
|
||||
return MainWindow.Instance.CurrentAssemblyList?.GetAssemblies().Any(l => l.HasLoadError) == true;
|
||||
return MainWindow.Instance.AssemblyTreeModel.CurrentAssemblyList?.GetAssemblies().Any(l => l.HasLoadError) == true;
|
||||
}
|
||||
|
||||
public override void Execute(object parameter)
|
||||
{
|
||||
foreach (var asm in MainWindow.Instance.CurrentAssemblyList.GetAssemblies())
|
||||
foreach (var asm in MainWindow.Instance.AssemblyTreeModel.CurrentAssemblyList.GetAssemblies())
|
||||
{
|
||||
if (!asm.HasLoadError)
|
||||
continue;
|
||||
var node = MainWindow.Instance.AssemblyListTreeNode.FindAssemblyNode(asm);
|
||||
var node = MainWindow.Instance.AssemblyTreeModel.FindAssemblyNode(asm);
|
||||
if (node != null && node.CanDelete())
|
||||
node.Delete();
|
||||
}
|
||||
@@ -51,12 +51,12 @@ namespace ICSharpCode.ILSpy
|
||||
{
|
||||
public override bool CanExecute(object parameter)
|
||||
{
|
||||
return MainWindow.Instance.CurrentAssemblyList?.Count > 0;
|
||||
return MainWindow.Instance.AssemblyTreeModel.CurrentAssemblyList?.Count > 0;
|
||||
}
|
||||
|
||||
public override void Execute(object parameter)
|
||||
{
|
||||
MainWindow.Instance.CurrentAssemblyList?.Clear();
|
||||
MainWindow.Instance.AssemblyTreeModel.CurrentAssemblyList?.Clear();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -32,7 +32,6 @@ using Microsoft.Win32;
|
||||
using ICSharpCode.ILSpyX.TreeView;
|
||||
using System.ComponentModel.Composition;
|
||||
|
||||
using ICSharpCode.ILSpy.Util;
|
||||
|
||||
namespace ICSharpCode.ILSpy.TextView
|
||||
{
|
||||
|
||||
@@ -48,10 +48,10 @@ namespace ICSharpCode.ILSpy
|
||||
await assembly.LoadDebugInfo(dlg.FileName);
|
||||
}
|
||||
|
||||
var node = (AssemblyTreeNode)MainWindow.Instance.FindNodeByPath(new[] { assembly.FileName }, true);
|
||||
var node = (AssemblyTreeNode)MainWindow.Instance.AssemblyTreeModel.FindNodeByPath(new[] { assembly.FileName }, true);
|
||||
node.UpdateToolTip();
|
||||
MainWindow.Instance.SelectNode(node);
|
||||
MainWindow.Instance.RefreshDecompiledView();
|
||||
MainWindow.Instance.AssemblyTreeModel.SelectNode(node);
|
||||
MainWindow.Instance.AssemblyTreeModel.RefreshDecompiledView();
|
||||
}
|
||||
|
||||
public bool IsEnabled(TextViewContext context) => true;
|
||||
|
||||
@@ -1,5 +1,4 @@
|
||||
using ICSharpCode.ILSpy.Util;
|
||||
|
||||
|
||||
namespace ICSharpCode.ILSpy.Commands
|
||||
{
|
||||
public class SetThemeCommand : SimpleCommand
|
||||
|
||||
@@ -6,7 +6,6 @@ using System.Windows;
|
||||
using ICSharpCode.Decompiler.FlowAnalysis;
|
||||
using ICSharpCode.Decompiler.IL;
|
||||
using ICSharpCode.Decompiler.IL.ControlFlow;
|
||||
using ICSharpCode.ILSpy.Util;
|
||||
|
||||
namespace ICSharpCode.ILSpy.Commands
|
||||
{
|
||||
|
||||
@@ -29,17 +29,11 @@ namespace ICSharpCode.ILSpy
|
||||
[ExportMainMenuCommand(ParentMenuID = nameof(Resources._View), Header = nameof(Resources.SortAssembly_listName), MenuIcon = "Images/Sort", MenuCategory = nameof(Resources.View))]
|
||||
[ExportToolbarCommand(ToolTip = nameof(Resources.SortAssemblyListName), ToolbarIcon = "Images/Sort", ToolbarCategory = nameof(Resources.View))]
|
||||
[PartCreationPolicy(CreationPolicy.Shared)]
|
||||
sealed class SortAssemblyListCommand : SimpleCommand, IComparer<LoadedAssembly>
|
||||
sealed class SortAssemblyListCommand : SimpleCommand
|
||||
{
|
||||
public override void Execute(object parameter)
|
||||
{
|
||||
using (MainWindow.Instance.AssemblyTreeView.LockUpdates())
|
||||
MainWindow.Instance.CurrentAssemblyList.Sort(this);
|
||||
}
|
||||
|
||||
int IComparer<LoadedAssembly>.Compare(LoadedAssembly x, LoadedAssembly y)
|
||||
{
|
||||
return string.Compare(x.ShortName, y.ShortName, StringComparison.CurrentCulture);
|
||||
MainWindow.Instance.AssemblyTreeModel.SortAssemblyList();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -50,19 +44,8 @@ namespace ICSharpCode.ILSpy
|
||||
{
|
||||
public override void Execute(object parameter)
|
||||
{
|
||||
using (MainWindow.Instance.AssemblyTreeView.LockUpdates())
|
||||
CollapseChildren(MainWindow.Instance.AssemblyTreeView.Root);
|
||||
MainWindow.Instance.AssemblyTreeModel.CollapseAll();
|
||||
|
||||
void CollapseChildren(SharpTreeNode node)
|
||||
{
|
||||
foreach (var child in node.Children)
|
||||
{
|
||||
if (!child.IsExpanded)
|
||||
continue;
|
||||
CollapseChildren(child);
|
||||
child.IsExpanded = false;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -19,6 +19,7 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.ComponentModel.Composition;
|
||||
using System.Diagnostics;
|
||||
using System.Linq;
|
||||
using System.Windows;
|
||||
using System.Windows.Controls;
|
||||
@@ -32,6 +33,7 @@ using ICSharpCode.ILSpy.Controls.TreeView;
|
||||
using ICSharpCode.ILSpyX.TreeView;
|
||||
|
||||
using TomsToolbox.Composition;
|
||||
using TomsToolbox.Essentials;
|
||||
|
||||
namespace ICSharpCode.ILSpy
|
||||
{
|
||||
@@ -168,6 +170,13 @@ namespace ICSharpCode.ILSpy
|
||||
|
||||
internal class ContextMenuProvider
|
||||
{
|
||||
private static readonly WeakEventSource<EventArgs> ContextMenuClosedEventSource = new();
|
||||
|
||||
public static event EventHandler<EventArgs> ContextMenuClosed {
|
||||
add => ContextMenuClosedEventSource.Subscribe(value);
|
||||
remove => ContextMenuClosedEventSource.Unsubscribe(value);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Enables extensible context menu support for the specified tree view.
|
||||
/// </summary>
|
||||
@@ -203,37 +212,40 @@ namespace ICSharpCode.ILSpy
|
||||
dataGrid.ContextMenu = new ContextMenu();
|
||||
}
|
||||
|
||||
readonly Control control;
|
||||
readonly SharpTreeView treeView;
|
||||
readonly DecompilerTextView textView;
|
||||
readonly ListBox listBox;
|
||||
readonly DataGrid dataGrid;
|
||||
readonly IExport<IContextMenuEntry, IContextMenuEntryMetadata>[] entries;
|
||||
|
||||
private ContextMenuProvider()
|
||||
private ContextMenuProvider(Control control)
|
||||
{
|
||||
entries = App.ExportProvider.GetExports<IContextMenuEntry, IContextMenuEntryMetadata>().ToArray();
|
||||
|
||||
this.control = control;
|
||||
}
|
||||
|
||||
ContextMenuProvider(DecompilerTextView textView)
|
||||
: this()
|
||||
: this((Control)textView)
|
||||
{
|
||||
this.textView = textView ?? throw new ArgumentNullException(nameof(textView));
|
||||
}
|
||||
|
||||
ContextMenuProvider(SharpTreeView treeView)
|
||||
: this()
|
||||
: this((Control)treeView)
|
||||
{
|
||||
this.treeView = treeView ?? throw new ArgumentNullException(nameof(treeView));
|
||||
}
|
||||
|
||||
ContextMenuProvider(ListBox listBox)
|
||||
: this()
|
||||
: this((Control)listBox)
|
||||
{
|
||||
this.listBox = listBox ?? throw new ArgumentNullException(nameof(listBox));
|
||||
}
|
||||
|
||||
ContextMenuProvider(DataGrid dataGrid)
|
||||
: this()
|
||||
: this((Control)dataGrid)
|
||||
{
|
||||
this.dataGrid = dataGrid ?? throw new ArgumentNullException(nameof(dataGrid));
|
||||
}
|
||||
@@ -289,7 +301,18 @@ namespace ICSharpCode.ILSpy
|
||||
|
||||
bool ShowContextMenu(TextViewContext context, out ContextMenu menu)
|
||||
{
|
||||
// Closing event is raised on the control where mouse is clicked, not on the control that opened the menu, so we hook on the global window event.
|
||||
var window = Window.GetWindow(control)!;
|
||||
window.ContextMenuClosing += ContextMenu_Closing;
|
||||
|
||||
void ContextMenu_Closing(object sender, EventArgs e)
|
||||
{
|
||||
window.ContextMenuClosing -= ContextMenu_Closing;
|
||||
ContextMenuClosedEventSource.Raise(this, EventArgs.Empty);
|
||||
}
|
||||
|
||||
menu = new ContextMenu();
|
||||
|
||||
var menuGroups = new Dictionary<string, IExport<IContextMenuEntry, IContextMenuEntryMetadata>[]>();
|
||||
IExport<IContextMenuEntry, IContextMenuEntryMetadata>[] topLevelGroup = null;
|
||||
foreach (var group in entries.OrderBy(c => c.Metadata.Order).GroupBy(c => c.Metadata.ParentMenuID))
|
||||
|
||||
@@ -158,6 +158,7 @@ namespace ICSharpCode.ILSpy.Controls.TreeView
|
||||
if (flattener != null)
|
||||
{
|
||||
flattener.Stop();
|
||||
flattener.CollectionChanged -= flattener_CollectionChanged;
|
||||
}
|
||||
if (Root != null)
|
||||
{
|
||||
|
||||
@@ -33,7 +33,6 @@ using ICSharpCode.AvalonEdit.Highlighting;
|
||||
using ICSharpCode.ILSpy.Analyzers;
|
||||
using ICSharpCode.ILSpy.Search;
|
||||
using ICSharpCode.ILSpy.TextView;
|
||||
using ICSharpCode.ILSpy.Util;
|
||||
using ICSharpCode.ILSpy.ViewModels;
|
||||
|
||||
using TomsToolbox.Wpf;
|
||||
@@ -136,8 +135,7 @@ namespace ICSharpCode.ILSpy.Docking
|
||||
{
|
||||
if (state.DecompiledNodes != null)
|
||||
{
|
||||
MainWindow.Instance.SelectNodes(state.DecompiledNodes,
|
||||
inNewTabPage: false, setFocus: true, changingActiveTab: true);
|
||||
MainWindow.Instance.AssemblyTreeModel.SelectNodes(state.DecompiledNodes, inNewTabPage: false, setFocus: true, changingTab: true);
|
||||
}
|
||||
else
|
||||
{
|
||||
@@ -216,7 +214,7 @@ namespace ICSharpCode.ILSpy.Docking
|
||||
CloseAllTabs();
|
||||
SessionSettings.DockLayout.Reset();
|
||||
InitializeLayout(MainWindow.Instance.dockManager);
|
||||
MainWindow.Instance.Dispatcher.BeginInvoke(DispatcherPriority.Background, (Action)MainWindow.Instance.RefreshDecompiledView);
|
||||
MainWindow.Instance.Dispatcher.BeginInvoke(DispatcherPriority.Background, (Action)MainWindow.Instance.AssemblyTreeModel.RefreshDecompiledView);
|
||||
}
|
||||
|
||||
static readonly PropertyInfo previousContainerProperty = typeof(LayoutContent).GetProperty("PreviousContainer", BindingFlags.NonPublic | BindingFlags.Instance);
|
||||
|
||||
@@ -27,7 +27,6 @@ using System.Windows.Media;
|
||||
|
||||
using ICSharpCode.Decompiler.Metadata;
|
||||
using ICSharpCode.Decompiler.TypeSystem;
|
||||
using ICSharpCode.ILSpy.Util;
|
||||
using ICSharpCode.ILSpyX;
|
||||
|
||||
namespace ICSharpCode.ILSpy
|
||||
|
||||
@@ -0,0 +1 @@
|
||||
global using ICSharpCode.ILSpy.Util;
|
||||
@@ -23,7 +23,6 @@ using System.Linq;
|
||||
using System.Runtime.CompilerServices;
|
||||
using System.Xml.Linq;
|
||||
|
||||
using ICSharpCode.ILSpy.Util;
|
||||
using ICSharpCode.ILSpyX;
|
||||
|
||||
namespace ICSharpCode.ILSpy
|
||||
|
||||
@@ -34,7 +34,6 @@ using ICSharpCode.Decompiler.Disassembler;
|
||||
using ICSharpCode.Decompiler.Metadata;
|
||||
using ICSharpCode.Decompiler.TypeSystem;
|
||||
using ICSharpCode.Decompiler.Util;
|
||||
using ICSharpCode.ILSpy.Util;
|
||||
using ICSharpCode.ILSpyX;
|
||||
using ICSharpCode.ILSpyX.Extensions;
|
||||
|
||||
|
||||
@@ -41,7 +41,6 @@ using ICSharpCode.Decompiler.TypeSystem;
|
||||
using ICSharpCode.Decompiler.Util;
|
||||
using ICSharpCode.ILSpy.TextView;
|
||||
using ICSharpCode.ILSpy.TreeNodes;
|
||||
using ICSharpCode.ILSpy.Util;
|
||||
using ICSharpCode.ILSpyX;
|
||||
|
||||
using LanguageVersion = ICSharpCode.ILSpyX.LanguageVersion;
|
||||
@@ -359,15 +358,15 @@ namespace ICSharpCode.ILSpy
|
||||
|
||||
void AddReferenceWarningMessage(MetadataFile module, ITextOutput output)
|
||||
{
|
||||
var loadedAssembly = MainWindow.Instance.CurrentAssemblyList.GetAssemblies().FirstOrDefault(la => la.GetMetadataFileOrNull() == module);
|
||||
var loadedAssembly = MainWindow.Instance.AssemblyTreeModel.CurrentAssemblyList.GetAssemblies().FirstOrDefault(la => la.GetMetadataFileOrNull() == module);
|
||||
if (loadedAssembly == null || !loadedAssembly.LoadedAssemblyReferencesInfo.HasErrors)
|
||||
return;
|
||||
string line1 = Properties.Resources.WarningSomeAssemblyReference;
|
||||
string line2 = Properties.Resources.PropertyManuallyMissingReferencesListLoadedAssemblies;
|
||||
AddWarningMessage(module, output, line1, line2, Properties.Resources.ShowAssemblyLoad, Images.ViewCode, delegate {
|
||||
ILSpyTreeNode assemblyNode = MainWindow.Instance.FindTreeNode(module);
|
||||
ILSpyTreeNode assemblyNode = MainWindow.Instance.AssemblyTreeModel.FindTreeNode(module);
|
||||
assemblyNode.EnsureLazyChildren();
|
||||
MainWindow.Instance.SelectNode(assemblyNode.Children.OfType<ReferenceFolderTreeNode>().Single());
|
||||
MainWindow.Instance.AssemblyTreeModel.SelectNode(assemblyNode.Children.OfType<ReferenceFolderTreeNode>().Single());
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
@@ -30,7 +30,6 @@ using ICSharpCode.Decompiler.Solution;
|
||||
using ICSharpCode.Decompiler.TypeSystem;
|
||||
using ICSharpCode.Decompiler.Util;
|
||||
using ICSharpCode.ILSpy.TextView;
|
||||
using ICSharpCode.ILSpy.Util;
|
||||
using ICSharpCode.ILSpyX;
|
||||
|
||||
namespace ICSharpCode.ILSpy
|
||||
|
||||
+1
-45
@@ -21,52 +21,8 @@
|
||||
xmlns:themes="clr-namespace:ICSharpCode.ILSpy.Themes"
|
||||
xmlns:toms="urn:TomsToolbox"
|
||||
xmlns:viewModels="clr-namespace:ICSharpCode.ILSpy.ViewModels"
|
||||
xmlns:treeNodes="clr-namespace:ICSharpCode.ILSpy.TreeNodes"
|
||||
xmlns:util="clr-namespace:ICSharpCode.ILSpy.Util"
|
||||
d:DataContext="{d:DesignInstance local:MainWindowViewModel}">
|
||||
<Window.Resources>
|
||||
<tv:SharpTreeView x:Key="AssemblyTreeView"
|
||||
AutomationProperties.Name="Assemblies and Classes"
|
||||
SelectionChanged="TreeView_SelectionChanged"
|
||||
ShowRoot="False"
|
||||
AllowDropOrder="True"
|
||||
AllowDrop="True"
|
||||
BorderThickness="0" Visibility="Visible">
|
||||
<tv:SharpTreeView.ItemContainerStyle>
|
||||
<Style TargetType="tv:SharpTreeViewItem">
|
||||
<Setter Property="Template">
|
||||
<Setter.Value>
|
||||
<ControlTemplate TargetType="{x:Type tv:SharpTreeViewItem}" d:DataContext="{d:DesignInstance treeNodes:ILSpyTreeNode}">
|
||||
<Border Background="Transparent">
|
||||
<Border Background="{TemplateBinding Background}">
|
||||
<tv:SharpTreeNodeView x:Name="nodeView" HorizontalAlignment="Left" />
|
||||
</Border>
|
||||
</Border>
|
||||
<ControlTemplate.Triggers>
|
||||
<DataTrigger Binding="{Binding IsAutoLoaded}" Value="True">
|
||||
<Setter Property="Foreground" Value="SteelBlue" />
|
||||
</DataTrigger>
|
||||
<DataTrigger Binding="{Binding IsPublicAPI}" Value="False">
|
||||
<Setter Property="Foreground" Value="{DynamicResource {x:Static SystemColors.GrayTextBrushKey}}" />
|
||||
</DataTrigger>
|
||||
<Trigger Property="IsSelected" Value="True">
|
||||
<Setter TargetName="nodeView" Property="TextBackground" Value="{DynamicResource {x:Static SystemColors.HighlightBrushKey}}" />
|
||||
<Setter TargetName="nodeView" Property="Foreground" Value="{DynamicResource {x:Static SystemColors.HighlightTextBrushKey}}" />
|
||||
</Trigger>
|
||||
<Trigger Property="IsEnabled" Value="False">
|
||||
<Setter TargetName="nodeView" Property="Foreground" Value="{DynamicResource {x:Static SystemColors.GrayTextBrushKey}}" />
|
||||
</Trigger>
|
||||
</ControlTemplate.Triggers>
|
||||
</ControlTemplate>
|
||||
</Setter.Value>
|
||||
</Setter>
|
||||
</Style>
|
||||
</tv:SharpTreeView.ItemContainerStyle>
|
||||
</tv:SharpTreeView>
|
||||
|
||||
<DataTemplate DataType="{x:Type viewModels:AssemblyListPaneModel}">
|
||||
<ContentControl Content="{StaticResource AssemblyTreeView}" />
|
||||
</DataTemplate>
|
||||
|
||||
<DataTemplate DataType="{x:Type viewModels:TabPageModel}">
|
||||
<ContentPresenter Content="{Binding Content}" />
|
||||
@@ -223,7 +179,7 @@
|
||||
<!-- Update panel -->
|
||||
<Border DockPanel.Dock="Top" BorderBrush="Black" BorderThickness="1" Name="updatePanel" Visibility="Collapsed">
|
||||
<DockPanel KeyboardNavigation.TabNavigation="Contained">
|
||||
<Button DockPanel.Dock="Right" Click="updatePanelCloseButtonClick" MinWidth="0">X</Button>
|
||||
<Button DockPanel.Dock="Right" Click="UpdatePanelCloseButtonClick" MinWidth="0">X</Button>
|
||||
<StackPanel Orientation="Horizontal">
|
||||
<TextBlock Name="updatePanelMessage" Margin="4,0" VerticalAlignment="Center"
|
||||
Text="{x:Static properties:Resources.ILSpyVersionAvailable}" />
|
||||
|
||||
+33
-787
File diff suppressed because it is too large
Load Diff
@@ -97,7 +97,7 @@ namespace ICSharpCode.ILSpy.Metadata
|
||||
|
||||
public void OnParentClick()
|
||||
{
|
||||
MainWindow.Instance.JumpToReference(new EntityReference("metadata", classLayout.Parent));
|
||||
MessageBus.Send(this, new NavigateToReferenceEventArgs(new EntityReference("metadata", classLayout.Parent)));
|
||||
}
|
||||
|
||||
string parentTooltip;
|
||||
|
||||
@@ -88,7 +88,7 @@ namespace ICSharpCode.ILSpy.Metadata
|
||||
|
||||
public void OnParentClick()
|
||||
{
|
||||
MainWindow.Instance.JumpToReference(new EntityReference(metadataFile, constant.Parent, protocol: "metadata"));
|
||||
MessageBus.Send(this, new NavigateToReferenceEventArgs(new EntityReference(metadataFile, constant.Parent, protocol: "metadata")));
|
||||
}
|
||||
|
||||
string parentTooltip;
|
||||
|
||||
@@ -83,7 +83,7 @@ namespace ICSharpCode.ILSpy.Metadata
|
||||
|
||||
public void OnParentClick()
|
||||
{
|
||||
MainWindow.Instance.JumpToReference(new EntityReference(metadataFile, customAttr.Parent, protocol: "metadata"));
|
||||
MessageBus.Send(this, new NavigateToReferenceEventArgs(new EntityReference(metadataFile, customAttr.Parent, protocol: "metadata")));
|
||||
}
|
||||
|
||||
string parentTooltip;
|
||||
@@ -94,7 +94,7 @@ namespace ICSharpCode.ILSpy.Metadata
|
||||
|
||||
public void OnConstructorClick()
|
||||
{
|
||||
MainWindow.Instance.JumpToReference(new EntityReference(metadataFile, customAttr.Constructor, protocol: "metadata"));
|
||||
MessageBus.Send(this, new NavigateToReferenceEventArgs(new EntityReference(metadataFile, customAttr.Constructor, protocol: "metadata")));
|
||||
}
|
||||
|
||||
string constructorTooltip;
|
||||
|
||||
@@ -84,7 +84,7 @@ namespace ICSharpCode.ILSpy.Metadata
|
||||
|
||||
public void OnParentClick()
|
||||
{
|
||||
MainWindow.Instance.JumpToReference(new EntityReference(metadataFile, declSecAttr.Parent, protocol: "metadata"));
|
||||
MessageBus.Send(this, new NavigateToReferenceEventArgs(new EntityReference(metadataFile, declSecAttr.Parent, protocol: "metadata")));
|
||||
}
|
||||
|
||||
string parentTooltip;
|
||||
|
||||
@@ -95,7 +95,7 @@ namespace ICSharpCode.ILSpy.Metadata
|
||||
|
||||
public void OnParentClick()
|
||||
{
|
||||
MainWindow.Instance.JumpToReference(new EntityReference(metadataFile, eventMap.Parent, protocol: "metadata"));
|
||||
MessageBus.Send(this, new NavigateToReferenceEventArgs(new EntityReference(metadataFile, eventMap.Parent, protocol: "metadata")));
|
||||
}
|
||||
|
||||
string parentTooltip;
|
||||
@@ -106,7 +106,7 @@ namespace ICSharpCode.ILSpy.Metadata
|
||||
|
||||
public void OnEventListClick()
|
||||
{
|
||||
MainWindow.Instance.JumpToReference(new EntityReference(metadataFile, eventMap.EventList, protocol: "metadata"));
|
||||
MessageBus.Send(this, new NavigateToReferenceEventArgs(new EntityReference(metadataFile, eventMap.EventList, protocol: "metadata")));
|
||||
}
|
||||
|
||||
string eventListTooltip;
|
||||
|
||||
@@ -103,7 +103,7 @@ namespace ICSharpCode.ILSpy.Metadata
|
||||
|
||||
public void OnTypeClick()
|
||||
{
|
||||
MainWindow.Instance.JumpToReference(new EntityReference(metadataFile, eventDef.Type, protocol: "metadata"));
|
||||
MessageBus.Send(this, new NavigateToReferenceEventArgs(new EntityReference(metadataFile, eventDef.Type, protocol: "metadata")));
|
||||
}
|
||||
|
||||
string typeTooltip;
|
||||
|
||||
@@ -107,7 +107,7 @@ namespace ICSharpCode.ILSpy.Metadata
|
||||
|
||||
public void OnImplementationClick()
|
||||
{
|
||||
MainWindow.Instance.JumpToReference(new EntityReference(metadataFile, type.Implementation, protocol: "metadata"));
|
||||
MessageBus.Send(this, new NavigateToReferenceEventArgs(new EntityReference(metadataFile, type.Implementation, protocol: "metadata")));
|
||||
}
|
||||
|
||||
string implementationTooltip;
|
||||
|
||||
@@ -96,7 +96,7 @@ namespace ICSharpCode.ILSpy.Metadata
|
||||
|
||||
public void OnFieldClick()
|
||||
{
|
||||
MainWindow.Instance.JumpToReference(new EntityReference(metadataFile, fieldLayout.Field, protocol: "metadata"));
|
||||
MessageBus.Send(this, new NavigateToReferenceEventArgs(new EntityReference(metadataFile, fieldLayout.Field, protocol: "metadata")));
|
||||
}
|
||||
|
||||
string fieldTooltip;
|
||||
|
||||
@@ -95,7 +95,7 @@ namespace ICSharpCode.ILSpy.Metadata
|
||||
|
||||
public void OnParentClick()
|
||||
{
|
||||
MainWindow.Instance.JumpToReference(new EntityReference(metadataFile, fieldMarshal.Parent, protocol: "metadata"));
|
||||
MessageBus.Send(this, new NavigateToReferenceEventArgs(new EntityReference(metadataFile, fieldMarshal.Parent, protocol: "metadata")));
|
||||
}
|
||||
|
||||
string parentTooltip;
|
||||
|
||||
@@ -99,7 +99,7 @@ namespace ICSharpCode.ILSpy.Metadata
|
||||
|
||||
public void OnFieldClick()
|
||||
{
|
||||
MainWindow.Instance.JumpToReference(new EntityReference(metadataFile, fieldRVA.Field, protocol: "metadata"));
|
||||
MessageBus.Send(this, new NavigateToReferenceEventArgs(new EntityReference(metadataFile, fieldRVA.Field, protocol: "metadata")));
|
||||
}
|
||||
|
||||
string fieldTooltip;
|
||||
|
||||
@@ -84,7 +84,7 @@ namespace ICSharpCode.ILSpy.Metadata
|
||||
|
||||
public void OnOwnerClick()
|
||||
{
|
||||
MainWindow.Instance.JumpToReference(new EntityReference(metadataFile, genericParamConstraint.Parameter, protocol: "metadata"));
|
||||
MessageBus.Send(this, new NavigateToReferenceEventArgs(new EntityReference(metadataFile, genericParamConstraint.Parameter, protocol: "metadata")));
|
||||
}
|
||||
|
||||
string ownerTooltip;
|
||||
@@ -108,7 +108,7 @@ namespace ICSharpCode.ILSpy.Metadata
|
||||
|
||||
public void OnTypeClick()
|
||||
{
|
||||
MainWindow.Instance.JumpToReference(new EntityReference(metadataFile, genericParamConstraint.Type, protocol: "metadata"));
|
||||
MessageBus.Send(this, new NavigateToReferenceEventArgs(new EntityReference(metadataFile, genericParamConstraint.Type, protocol: "metadata")));
|
||||
}
|
||||
|
||||
string typeTooltip;
|
||||
|
||||
@@ -92,7 +92,7 @@ namespace ICSharpCode.ILSpy.Metadata
|
||||
|
||||
public void OnOwnerClick()
|
||||
{
|
||||
MainWindow.Instance.JumpToReference(new EntityReference(metadataFile, genericParam.Parent, protocol: "metadata"));
|
||||
MessageBus.Send(this, new NavigateToReferenceEventArgs(new EntityReference(metadataFile, genericParam.Parent, protocol: "metadata")));
|
||||
}
|
||||
|
||||
string ownerTooltip;
|
||||
|
||||
@@ -113,7 +113,7 @@ namespace ICSharpCode.ILSpy.Metadata
|
||||
|
||||
public void OnMemberForwardedClick()
|
||||
{
|
||||
MainWindow.Instance.JumpToReference(new EntityReference(metadataFile, implMap.MemberForwarded, protocol: "metadata"));
|
||||
MessageBus.Send(this, new NavigateToReferenceEventArgs(new EntityReference(metadataFile, implMap.MemberForwarded, protocol: "metadata")));
|
||||
}
|
||||
|
||||
string memberForwardedTooltip;
|
||||
@@ -124,7 +124,7 @@ namespace ICSharpCode.ILSpy.Metadata
|
||||
|
||||
public void OnImportScopeClick()
|
||||
{
|
||||
MainWindow.Instance.JumpToReference(new EntityReference(metadataFile, implMap.ImportScope, protocol: "metadata"));
|
||||
MessageBus.Send(this, new NavigateToReferenceEventArgs(new EntityReference(metadataFile, implMap.ImportScope, protocol: "metadata")));
|
||||
}
|
||||
|
||||
string importScopeTooltip;
|
||||
|
||||
@@ -96,7 +96,7 @@ namespace ICSharpCode.ILSpy.Metadata
|
||||
|
||||
public void OnClassClick()
|
||||
{
|
||||
MainWindow.Instance.JumpToReference(new EntityReference(metadataFile, interfaceImpl.Class, protocol: "metadata"));
|
||||
MessageBus.Send(this, new NavigateToReferenceEventArgs(new EntityReference(metadataFile, interfaceImpl.Class, protocol: "metadata")));
|
||||
}
|
||||
|
||||
string classTooltip;
|
||||
@@ -107,7 +107,7 @@ namespace ICSharpCode.ILSpy.Metadata
|
||||
|
||||
public void OnInterfaceClick()
|
||||
{
|
||||
MainWindow.Instance.JumpToReference(new EntityReference(metadataFile, interfaceImpl.Interface, protocol: "metadata"));
|
||||
MessageBus.Send(this, new NavigateToReferenceEventArgs(new EntityReference(metadataFile, interfaceImpl.Interface, protocol: "metadata")));
|
||||
}
|
||||
|
||||
string interfaceTooltip;
|
||||
|
||||
@@ -93,7 +93,7 @@ namespace ICSharpCode.ILSpy.Metadata
|
||||
|
||||
public void OnImplementationClick()
|
||||
{
|
||||
MainWindow.Instance.JumpToReference(new EntityReference(metadataFile, manifestResource.Implementation, protocol: "metadata"));
|
||||
MessageBus.Send(this, new NavigateToReferenceEventArgs(new EntityReference(metadataFile, manifestResource.Implementation, protocol: "metadata")));
|
||||
}
|
||||
|
||||
string implementationTooltip;
|
||||
|
||||
@@ -83,7 +83,7 @@ namespace ICSharpCode.ILSpy.Metadata
|
||||
|
||||
public void OnParentClick()
|
||||
{
|
||||
MainWindow.Instance.JumpToReference(new EntityReference(metadataFile, memberRef.Parent, protocol: "metadata"));
|
||||
MessageBus.Send(this, new NavigateToReferenceEventArgs(new EntityReference(metadataFile, memberRef.Parent, protocol: "metadata")));
|
||||
}
|
||||
|
||||
string parentTooltip;
|
||||
|
||||
@@ -82,7 +82,7 @@ namespace ICSharpCode.ILSpy.Metadata
|
||||
|
||||
public void OnMethodDeclarationClick()
|
||||
{
|
||||
MainWindow.Instance.JumpToReference(new EntityReference(metadataFile, methodImpl.MethodDeclaration, protocol: "metadata"));
|
||||
MessageBus.Send(this, new NavigateToReferenceEventArgs(new EntityReference(metadataFile, methodImpl.MethodDeclaration, protocol: "metadata")));
|
||||
}
|
||||
|
||||
string methodDeclarationTooltip;
|
||||
@@ -93,7 +93,7 @@ namespace ICSharpCode.ILSpy.Metadata
|
||||
|
||||
public void OnMethodBodyClick()
|
||||
{
|
||||
MainWindow.Instance.JumpToReference(new EntityReference(metadataFile, methodImpl.MethodBody, protocol: "metadata"));
|
||||
MessageBus.Send(this, new NavigateToReferenceEventArgs(new EntityReference(metadataFile, methodImpl.MethodBody, protocol: "metadata")));
|
||||
}
|
||||
|
||||
string methodBodyTooltip;
|
||||
@@ -104,7 +104,7 @@ namespace ICSharpCode.ILSpy.Metadata
|
||||
|
||||
public void OnTypeClick()
|
||||
{
|
||||
MainWindow.Instance.JumpToReference(new EntityReference(metadataFile, methodImpl.Type, protocol: "metadata"));
|
||||
MessageBus.Send(this, new NavigateToReferenceEventArgs(new EntityReference(metadataFile, methodImpl.Type, protocol: "metadata")));
|
||||
}
|
||||
|
||||
string typeTooltip;
|
||||
|
||||
@@ -90,7 +90,7 @@ namespace ICSharpCode.ILSpy.Metadata
|
||||
|
||||
public void OnMethodClick()
|
||||
{
|
||||
MainWindow.Instance.JumpToReference(new EntityReference(metadataFile, method, protocol: "metadata"));
|
||||
MessageBus.Send(this, new NavigateToReferenceEventArgs(new EntityReference(metadataFile, method, protocol: "metadata")));
|
||||
}
|
||||
|
||||
string methodTooltip;
|
||||
@@ -101,7 +101,7 @@ namespace ICSharpCode.ILSpy.Metadata
|
||||
|
||||
public void OnAssociationClick()
|
||||
{
|
||||
MainWindow.Instance.JumpToReference(new EntityReference(metadataFile, association, protocol: "metadata"));
|
||||
MessageBus.Send(this, new NavigateToReferenceEventArgs(new EntityReference(metadataFile, association, protocol: "metadata")));
|
||||
}
|
||||
|
||||
string associationTooltip;
|
||||
|
||||
@@ -85,7 +85,7 @@ namespace ICSharpCode.ILSpy.Metadata
|
||||
|
||||
public void OnMethodClick()
|
||||
{
|
||||
MainWindow.Instance.JumpToReference(new EntityReference(metadataFile, methodSpec.Method, protocol: "metadata"));
|
||||
MessageBus.Send(this, new NavigateToReferenceEventArgs(new EntityReference(metadataFile, methodSpec.Method, protocol: "metadata")));
|
||||
}
|
||||
|
||||
string methodTooltip;
|
||||
|
||||
@@ -118,7 +118,7 @@ namespace ICSharpCode.ILSpy.Metadata
|
||||
|
||||
public void OnParamListClick()
|
||||
{
|
||||
MainWindow.Instance.JumpToReference(new EntityReference(metadataFile, methodDef.GetParameters().FirstOrDefault(), protocol: "metadata"));
|
||||
MessageBus.Send(this, new NavigateToReferenceEventArgs(new EntityReference(metadataFile, methodDef.GetParameters().FirstOrDefault(), protocol: "metadata")));
|
||||
}
|
||||
|
||||
string paramListTooltip;
|
||||
|
||||
@@ -95,7 +95,7 @@ namespace ICSharpCode.ILSpy.Metadata
|
||||
|
||||
public void OnNestedClassClick()
|
||||
{
|
||||
MainWindow.Instance.JumpToReference(new EntityReference(metadataFile, nestedClass.Nested, protocol: "metadata"));
|
||||
MessageBus.Send(this, new NavigateToReferenceEventArgs(new EntityReference(metadataFile, nestedClass.Nested, protocol: "metadata")));
|
||||
}
|
||||
|
||||
string nestedClassTooltip;
|
||||
@@ -106,7 +106,7 @@ namespace ICSharpCode.ILSpy.Metadata
|
||||
|
||||
public void OnEnclosingClassClick()
|
||||
{
|
||||
MainWindow.Instance.JumpToReference(new EntityReference(metadataFile, nestedClass.Enclosing, protocol: "metadata"));
|
||||
MessageBus.Send(this, new NavigateToReferenceEventArgs(new EntityReference(metadataFile, nestedClass.Enclosing, protocol: "metadata")));
|
||||
}
|
||||
|
||||
string enclosingClassTooltip;
|
||||
|
||||
@@ -95,7 +95,7 @@ namespace ICSharpCode.ILSpy.Metadata
|
||||
|
||||
public void OnParentClick()
|
||||
{
|
||||
MainWindow.Instance.JumpToReference(new EntityReference(metadataFile, propertyMap.Parent, protocol: "metadata"));
|
||||
MessageBus.Send(this, new NavigateToReferenceEventArgs(new EntityReference(metadataFile, propertyMap.Parent, protocol: "metadata")));
|
||||
}
|
||||
|
||||
string parentTooltip;
|
||||
@@ -106,7 +106,7 @@ namespace ICSharpCode.ILSpy.Metadata
|
||||
|
||||
public void OnPropertyListClick()
|
||||
{
|
||||
MainWindow.Instance.JumpToReference(new EntityReference(metadataFile, propertyMap.PropertyList, protocol: "metadata"));
|
||||
MessageBus.Send(this, new NavigateToReferenceEventArgs(new EntityReference(metadataFile, propertyMap.PropertyList, protocol: "metadata")));
|
||||
}
|
||||
|
||||
string propertyListTooltip;
|
||||
|
||||
@@ -111,7 +111,7 @@ namespace ICSharpCode.ILSpy.Metadata
|
||||
|
||||
public void OnBaseTypeClick()
|
||||
{
|
||||
MainWindow.Instance.JumpToReference(new EntityReference(metadataFile, typeDef.BaseType, protocol: "metadata"));
|
||||
MessageBus.Send(this, new NavigateToReferenceEventArgs(new EntityReference(metadataFile, typeDef.BaseType, protocol: "metadata")));
|
||||
}
|
||||
|
||||
public string BaseTypeTooltip {
|
||||
@@ -142,7 +142,7 @@ namespace ICSharpCode.ILSpy.Metadata
|
||||
|
||||
public void OnFieldListClick()
|
||||
{
|
||||
MainWindow.Instance.JumpToReference(new EntityReference(metadataFile, typeDef.GetFields().FirstOrDefault(), protocol: "metadata"));
|
||||
MessageBus.Send(this, new NavigateToReferenceEventArgs(new EntityReference(metadataFile, typeDef.GetFields().FirstOrDefault(), protocol: "metadata")));
|
||||
}
|
||||
|
||||
string fieldListTooltip;
|
||||
@@ -160,7 +160,7 @@ namespace ICSharpCode.ILSpy.Metadata
|
||||
|
||||
public void OnMethodListClick()
|
||||
{
|
||||
MainWindow.Instance.JumpToReference(new EntityReference(metadataFile, typeDef.GetMethods().FirstOrDefault(), protocol: "metadata"));
|
||||
MessageBus.Send(this, new NavigateToReferenceEventArgs(new EntityReference(metadataFile, typeDef.GetMethods().FirstOrDefault(), protocol: "metadata")));
|
||||
}
|
||||
|
||||
string methodListTooltip;
|
||||
|
||||
@@ -83,7 +83,7 @@ namespace ICSharpCode.ILSpy.Metadata
|
||||
|
||||
public void OnResolutionScopeClick()
|
||||
{
|
||||
MainWindow.Instance.JumpToReference(new EntityReference(metadataFile, typeRef.ResolutionScope, protocol: "metadata"));
|
||||
MessageBus.Send(this, new NavigateToReferenceEventArgs(new EntityReference(metadataFile, typeRef.ResolutionScope, protocol: "metadata")));
|
||||
}
|
||||
|
||||
string resolutionScopeTooltip;
|
||||
|
||||
@@ -21,7 +21,6 @@ using System.Reflection.Metadata.Ecma335;
|
||||
using ICSharpCode.Decompiler;
|
||||
using ICSharpCode.Decompiler.Metadata;
|
||||
using ICSharpCode.ILSpy.TreeNodes;
|
||||
using ICSharpCode.ILSpy.Util;
|
||||
using ICSharpCode.ILSpy.ViewModels;
|
||||
|
||||
namespace ICSharpCode.ILSpy.Metadata
|
||||
|
||||
@@ -188,7 +188,7 @@ namespace ICSharpCode.ILSpy.Metadata
|
||||
|
||||
public void OnParentClick()
|
||||
{
|
||||
MainWindow.Instance.JumpToReference(new EntityReference(metadataFile, debugInfo.Parent, protocol: "metadata"));
|
||||
MessageBus.Send(this, new NavigateToReferenceEventArgs(new EntityReference(metadataFile, debugInfo.Parent, protocol: "metadata")));
|
||||
}
|
||||
|
||||
string parentTooltip;
|
||||
|
||||
@@ -80,7 +80,7 @@ namespace ICSharpCode.ILSpy.Metadata
|
||||
|
||||
public void OnParentClick()
|
||||
{
|
||||
MainWindow.Instance.JumpToReference(new EntityReference(metadataFile, localScope.Parent, protocol: "metadata"));
|
||||
MessageBus.Send(this, new NavigateToReferenceEventArgs(new EntityReference(metadataFile, localScope.Parent, protocol: "metadata")));
|
||||
}
|
||||
|
||||
[ColumnInfo("X8", Kind = ColumnKind.HeapOffset)]
|
||||
|
||||
@@ -81,7 +81,7 @@ namespace ICSharpCode.ILSpy.Metadata
|
||||
|
||||
public void OnMethodClick()
|
||||
{
|
||||
MainWindow.Instance.JumpToReference(new EntityReference(metadataFile, localScope.Method, protocol: "metadata"));
|
||||
MessageBus.Send(this, new NavigateToReferenceEventArgs(new EntityReference(metadataFile, localScope.Method, protocol: "metadata")));
|
||||
}
|
||||
|
||||
string methodTooltip;
|
||||
@@ -92,7 +92,7 @@ namespace ICSharpCode.ILSpy.Metadata
|
||||
|
||||
public void OnImportScopeClick()
|
||||
{
|
||||
MainWindow.Instance.JumpToReference(new EntityReference(metadataFile, localScope.ImportScope, protocol: "metadata"));
|
||||
MessageBus.Send(this, new NavigateToReferenceEventArgs(new EntityReference(metadataFile, localScope.ImportScope, protocol: "metadata")));
|
||||
}
|
||||
|
||||
[ColumnInfo("X8", Kind = ColumnKind.Token)]
|
||||
@@ -100,7 +100,7 @@ namespace ICSharpCode.ILSpy.Metadata
|
||||
|
||||
public void OnVariableListClick()
|
||||
{
|
||||
MainWindow.Instance.JumpToReference(new EntityReference(metadataFile, localScope.GetLocalVariables().FirstOrDefault(), protocol: "metadata"));
|
||||
MessageBus.Send(this, new NavigateToReferenceEventArgs(new EntityReference(metadataFile, localScope.GetLocalVariables().FirstOrDefault(), protocol: "metadata")));
|
||||
}
|
||||
|
||||
[ColumnInfo("X8", Kind = ColumnKind.Token)]
|
||||
@@ -108,7 +108,7 @@ namespace ICSharpCode.ILSpy.Metadata
|
||||
|
||||
public void OnConstantListClick()
|
||||
{
|
||||
MainWindow.Instance.JumpToReference(new EntityReference(metadataFile, localScope.GetLocalConstants().FirstOrDefault(), protocol: "metadata"));
|
||||
MessageBus.Send(this, new NavigateToReferenceEventArgs(new EntityReference(metadataFile, localScope.GetLocalConstants().FirstOrDefault(), protocol: "metadata")));
|
||||
}
|
||||
|
||||
public int StartOffset => localScope.StartOffset;
|
||||
|
||||
@@ -83,7 +83,7 @@ namespace ICSharpCode.ILSpy.Metadata
|
||||
|
||||
public void OnDocumentClick()
|
||||
{
|
||||
MainWindow.Instance.JumpToReference(new EntityReference(metadataFile, debugInfo.Document, protocol: "metadata"));
|
||||
MessageBus.Send(this, new NavigateToReferenceEventArgs(new EntityReference(metadataFile, debugInfo.Document, protocol: "metadata")));
|
||||
}
|
||||
|
||||
public string DocumentTooltip {
|
||||
@@ -116,7 +116,7 @@ namespace ICSharpCode.ILSpy.Metadata
|
||||
|
||||
public void OnLocalSignatureClick()
|
||||
{
|
||||
MainWindow.Instance.JumpToReference(new EntityReference(metadataFile, debugInfo.LocalSignature, protocol: "metadata"));
|
||||
MessageBus.Send(this, new NavigateToReferenceEventArgs(new EntityReference(metadataFile, debugInfo.LocalSignature, protocol: "metadata")));
|
||||
}
|
||||
|
||||
public string LocalSignatureTooltip {
|
||||
|
||||
@@ -83,7 +83,7 @@ namespace ICSharpCode.ILSpy.Metadata
|
||||
|
||||
public void OnMoveNextMethodClick()
|
||||
{
|
||||
MainWindow.Instance.JumpToReference(new EntityReference(metadataFile, moveNextMethod, protocol: "metadata"));
|
||||
MessageBus.Send(this, new NavigateToReferenceEventArgs(new EntityReference(metadataFile, moveNextMethod, protocol: "metadata")));
|
||||
}
|
||||
|
||||
string moveNextMethodTooltip;
|
||||
@@ -94,7 +94,7 @@ namespace ICSharpCode.ILSpy.Metadata
|
||||
|
||||
public void OnKickofMethodClick()
|
||||
{
|
||||
MainWindow.Instance.JumpToReference(new EntityReference(metadataFile, kickoffMethod, protocol: "metadata"));
|
||||
MessageBus.Send(this, new NavigateToReferenceEventArgs(new EntityReference(metadataFile, kickoffMethod, protocol: "metadata")));
|
||||
}
|
||||
|
||||
string kickoffMethodTooltip;
|
||||
|
||||
@@ -38,7 +38,7 @@ namespace ICSharpCode.ILSpy.Commands
|
||||
public void Execute(TextViewContext context)
|
||||
{
|
||||
int token = GetSelectedToken(context.DataGrid, out MetadataFile module).Value;
|
||||
MainWindow.Instance.JumpToReference(new EntityReference(module, MetadataTokens.Handle(token), protocol: "metadata"));
|
||||
MessageBus.Send(this, new NavigateToReferenceEventArgs(new EntityReference(module, MetadataTokens.Handle(token), protocol: "metadata")));
|
||||
}
|
||||
|
||||
public bool IsEnabled(TextViewContext context)
|
||||
|
||||
@@ -34,7 +34,7 @@ namespace ICSharpCode.ILSpy.Metadata
|
||||
newTabPage = true;
|
||||
if (protocol != "metadata")
|
||||
return null;
|
||||
var assemblyTreeNode = MainWindow.Instance.FindTreeNode(module) as AssemblyTreeNode;
|
||||
var assemblyTreeNode = MainWindow.Instance.AssemblyTreeModel.FindTreeNode(module) as AssemblyTreeNode;
|
||||
if (assemblyTreeNode == null)
|
||||
return null;
|
||||
var mxNode = assemblyTreeNode.Children.OfType<MetadataTreeNode>().FirstOrDefault();
|
||||
|
||||
@@ -23,7 +23,6 @@ using System.Reflection.Metadata.Ecma335;
|
||||
using ICSharpCode.Decompiler;
|
||||
using ICSharpCode.Decompiler.Metadata;
|
||||
using ICSharpCode.ILSpy.TreeNodes;
|
||||
using ICSharpCode.ILSpy.Util;
|
||||
using ICSharpCode.ILSpy.ViewModels;
|
||||
|
||||
namespace ICSharpCode.ILSpy.Metadata
|
||||
|
||||
@@ -19,7 +19,6 @@
|
||||
using System.ComponentModel.Composition;
|
||||
using System.Xml.Linq;
|
||||
|
||||
using ICSharpCode.ILSpy.Util;
|
||||
using ICSharpCode.ILSpyX.Settings;
|
||||
|
||||
namespace ICSharpCode.ILSpy.Options
|
||||
|
||||
@@ -27,7 +27,6 @@ using System.Windows.Media;
|
||||
using System.Windows.Threading;
|
||||
using System.Xml.Linq;
|
||||
|
||||
using ICSharpCode.ILSpy.Util;
|
||||
using ICSharpCode.ILSpyX.Settings;
|
||||
|
||||
namespace ICSharpCode.ILSpy.Options
|
||||
|
||||
@@ -32,7 +32,6 @@ using System.Windows.Media;
|
||||
using System.Windows.Threading;
|
||||
|
||||
using ICSharpCode.ILSpy.AppEnv;
|
||||
using ICSharpCode.ILSpy.Util;
|
||||
using ICSharpCode.ILSpy.ViewModels;
|
||||
using ICSharpCode.ILSpyX;
|
||||
using ICSharpCode.ILSpyX.Extensions;
|
||||
@@ -250,8 +249,8 @@ namespace ICSharpCode.ILSpy.Search
|
||||
{
|
||||
|
||||
searchProgressBar.IsIndeterminate = true;
|
||||
startedSearch = new(await mainWindow.CurrentAssemblyList.GetAllAssemblies(), searchTerm,
|
||||
(SearchMode)searchModeComboBox.SelectedIndex, mainWindow.CurrentLanguage,
|
||||
startedSearch = new(await mainWindow.AssemblyTreeModel.CurrentAssemblyList.GetAllAssemblies(), searchTerm,
|
||||
(SearchMode)searchModeComboBox.SelectedIndex, mainWindow.AssemblyTreeModel.CurrentLanguage,
|
||||
SettingsService.Instance.SessionSettings.LanguageSettings.ShowApiLevel);
|
||||
currentSearch = startedSearch;
|
||||
|
||||
@@ -269,7 +268,7 @@ namespace ICSharpCode.ILSpy.Search
|
||||
{
|
||||
if (listBox.SelectedItem is SearchResult result)
|
||||
{
|
||||
MainWindow.Instance.JumpToReference(result.Reference);
|
||||
MessageBus.Send(this, new NavigateToReferenceEventArgs(result.Reference));
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -20,7 +20,6 @@ using System.ComponentModel.Composition;
|
||||
using System.Windows.Input;
|
||||
using System.Windows.Media;
|
||||
|
||||
using ICSharpCode.ILSpy.Util;
|
||||
using ICSharpCode.ILSpy.ViewModels;
|
||||
using ICSharpCode.ILSpyX.Search;
|
||||
|
||||
|
||||
@@ -28,7 +28,6 @@ using System.Xml.Linq;
|
||||
|
||||
using ICSharpCode.ILSpy.Docking;
|
||||
using ICSharpCode.ILSpy.Themes;
|
||||
using ICSharpCode.ILSpy.Util;
|
||||
using ICSharpCode.ILSpyX.Search;
|
||||
using ICSharpCode.ILSpyX.Settings;
|
||||
|
||||
|
||||
+1
-1
@@ -198,7 +198,7 @@ namespace ICSharpCode.ILSpy
|
||||
public static void HandleExceptions(this Task task)
|
||||
{
|
||||
task.Catch<Exception>(exception => MainWindow.Instance.Dispatcher.BeginInvoke(new Action(delegate {
|
||||
AvalonEditTextOutput output = new AvalonEditTextOutput();
|
||||
AvalonEditTextOutput output = new();
|
||||
output.Write(exception.ToString());
|
||||
Docking.DockWorkspace.Instance.ShowText(output);
|
||||
}))).IgnoreExceptions();
|
||||
|
||||
@@ -52,11 +52,11 @@ using ICSharpCode.Decompiler.CSharp.OutputVisitor;
|
||||
using ICSharpCode.Decompiler.CSharp.ProjectDecompiler;
|
||||
using ICSharpCode.Decompiler.Documentation;
|
||||
using ICSharpCode.Decompiler.TypeSystem;
|
||||
using ICSharpCode.ILSpy.AssemblyTree;
|
||||
using ICSharpCode.ILSpy.AvalonEdit;
|
||||
using ICSharpCode.ILSpy.Options;
|
||||
using ICSharpCode.ILSpy.Themes;
|
||||
using ICSharpCode.ILSpy.TreeNodes;
|
||||
using ICSharpCode.ILSpy.Util;
|
||||
using ICSharpCode.ILSpy.ViewModels;
|
||||
using ICSharpCode.ILSpyX;
|
||||
|
||||
@@ -414,7 +414,7 @@ namespace ICSharpCode.ILSpy.TextView
|
||||
}
|
||||
else if (segment.Reference is EntityReference unresolvedEntity)
|
||||
{
|
||||
var module = unresolvedEntity.ResolveAssembly(MainWindow.Instance.CurrentAssemblyList);
|
||||
var module = unresolvedEntity.ResolveAssembly(MainWindow.Instance.AssemblyTreeModel.CurrentAssemblyList);
|
||||
if (module == null)
|
||||
return null;
|
||||
var typeSystem = new DecompilerTypeSystem(module,
|
||||
@@ -474,7 +474,7 @@ namespace ICSharpCode.ILSpy.TextView
|
||||
|
||||
IEntity? ResolveReference(string idString)
|
||||
{
|
||||
return MainWindow.FindEntityInRelevantAssemblies(idString, MainWindow.Instance.CurrentAssemblyList.GetAssemblies());
|
||||
return AssemblyListPaneModel.FindEntityInRelevantAssemblies(idString, MainWindow.Instance.AssemblyTreeModel.CurrentAssemblyList.GetAssemblies());
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1001,7 +1001,7 @@ namespace ICSharpCode.ILSpy.TextView
|
||||
return;
|
||||
}
|
||||
}
|
||||
MainWindow.Instance.JumpToReference(reference, openInNewTab);
|
||||
MessageBus.Send(this, new NavigateToReferenceEventArgs(reference, openInNewTab));
|
||||
}
|
||||
|
||||
Point? mouseDownPos;
|
||||
|
||||
@@ -37,7 +37,6 @@ using ICSharpCode.Decompiler.Documentation;
|
||||
using ICSharpCode.Decompiler.Output;
|
||||
using ICSharpCode.Decompiler.TypeSystem;
|
||||
using ICSharpCode.ILSpy.Options;
|
||||
using ICSharpCode.ILSpy.Util;
|
||||
|
||||
namespace ICSharpCode.ILSpy.TextView
|
||||
{
|
||||
@@ -339,7 +338,7 @@ namespace ICSharpCode.ILSpy.TextView
|
||||
{
|
||||
var h = new Hyperlink(new Run(ambience.ConvertSymbol(referencedEntity)));
|
||||
h.Click += (sender, e) => {
|
||||
MainWindow.Instance.JumpToReference(referencedEntity);
|
||||
MessageBus.Send(this, new NavigateToReferenceEventArgs(referencedEntity));
|
||||
};
|
||||
return h;
|
||||
}
|
||||
@@ -382,7 +381,7 @@ namespace ICSharpCode.ILSpy.TextView
|
||||
{
|
||||
Hyperlink link = new Hyperlink();
|
||||
link.Click += (sender, e) => {
|
||||
MainWindow.Instance.JumpToReference(referencedEntity);
|
||||
MessageBus.Send(this, new NavigateToReferenceEventArgs(referencedEntity));
|
||||
};
|
||||
AddSpan(link, element.Children);
|
||||
}
|
||||
|
||||
@@ -24,7 +24,6 @@ using System.Windows.Interop;
|
||||
using System.Windows.Media;
|
||||
|
||||
using ICSharpCode.ILSpy.Options;
|
||||
using ICSharpCode.ILSpy.Util;
|
||||
|
||||
using TomsToolbox.Essentials;
|
||||
using TomsToolbox.Wpf;
|
||||
|
||||
@@ -24,10 +24,9 @@ using System.Windows;
|
||||
using ICSharpCode.Decompiler;
|
||||
using ICSharpCode.Decompiler.Metadata;
|
||||
using ICSharpCode.Decompiler.TypeSystem;
|
||||
using ICSharpCode.Decompiler.Util;
|
||||
using ICSharpCode.ILSpyX;
|
||||
using ICSharpCode.ILSpyX.TreeView.PlatformAbstractions;
|
||||
using ICSharpCode.ILSpyX.TreeView;
|
||||
using ICSharpCode.ILSpyX.TreeView.PlatformAbstractions;
|
||||
|
||||
namespace ICSharpCode.ILSpy.TreeNodes
|
||||
{
|
||||
@@ -87,13 +86,10 @@ namespace ICSharpCode.ILSpy.TreeNodes
|
||||
e.Effects = XPlatDragDropEffects.Move | XPlatDragDropEffects.Copy | XPlatDragDropEffects.Link;
|
||||
if (e.Data.GetDataPresent(AssemblyTreeNode.DataFormat))
|
||||
return true;
|
||||
else if (e.Data.GetDataPresent(DataFormats.FileDrop))
|
||||
if (e.Data.GetDataPresent(DataFormats.FileDrop))
|
||||
return true;
|
||||
else
|
||||
{
|
||||
e.Effects = XPlatDragDropEffects.None;
|
||||
return false;
|
||||
}
|
||||
e.Effects = XPlatDragDropEffects.None;
|
||||
return false;
|
||||
}
|
||||
|
||||
public override void Drop(IPlatformDragEventArgs e, int index)
|
||||
@@ -110,8 +106,8 @@ namespace ICSharpCode.ILSpy.TreeNodes
|
||||
.Distinct()
|
||||
.ToArray();
|
||||
assemblyList.Move(assemblies, index);
|
||||
var nodes = assemblies.SelectArray(MainWindow.Instance.FindTreeNode);
|
||||
MainWindow.Instance.SelectNodes(nodes);
|
||||
var nodes = assemblies.SelectArray(MainWindow.Instance.AssemblyTreeModel.FindTreeNode);
|
||||
MainWindow.Instance.AssemblyTreeModel.SelectNodes(nodes);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -187,7 +183,7 @@ namespace ICSharpCode.ILSpy.TreeNodes
|
||||
if (bundle == null)
|
||||
return null;
|
||||
bundle.EnsureLazyChildren();
|
||||
foreach (var node in ILSpyX.TreeView.TreeTraversal.PreOrder(bundle.Children, ExpandAndGetChildren).OfType<AssemblyTreeNode>())
|
||||
foreach (var node in TreeTraversal.PreOrder(bundle.Children, ExpandAndGetChildren).OfType<AssemblyTreeNode>())
|
||||
{
|
||||
if (node.LoadedAssembly == asm)
|
||||
return node;
|
||||
|
||||
@@ -26,7 +26,6 @@ using ICSharpCode.Decompiler;
|
||||
using ICSharpCode.Decompiler.Metadata;
|
||||
using ICSharpCode.Decompiler.TypeSystem;
|
||||
using ICSharpCode.ILSpy.Themes;
|
||||
using ICSharpCode.ILSpy.Util;
|
||||
using ICSharpCode.ILSpyX.TreeView.PlatformAbstractions;
|
||||
|
||||
namespace ICSharpCode.ILSpy.TreeNodes
|
||||
|
||||
@@ -30,10 +30,10 @@ using ICSharpCode.Decompiler;
|
||||
using ICSharpCode.Decompiler.CSharp.ProjectDecompiler;
|
||||
using ICSharpCode.Decompiler.Metadata;
|
||||
using ICSharpCode.Decompiler.TypeSystem;
|
||||
using ICSharpCode.ILSpy.AssemblyTree;
|
||||
using ICSharpCode.ILSpy.Controls.TreeView;
|
||||
using ICSharpCode.ILSpy.Metadata;
|
||||
using ICSharpCode.ILSpy.Properties;
|
||||
using ICSharpCode.ILSpy.Util;
|
||||
using ICSharpCode.ILSpy.ViewModels;
|
||||
using ICSharpCode.ILSpyX;
|
||||
using ICSharpCode.ILSpyX.FileLoaders;
|
||||
@@ -630,13 +630,13 @@ namespace ICSharpCode.ILSpy.TreeNodes
|
||||
{
|
||||
foreach (var node in context.SelectedTreeNodes)
|
||||
{
|
||||
paths.Add(MainWindow.GetPathForNode(node));
|
||||
paths.Add(AssemblyListPaneModel.GetPathForNode(node));
|
||||
var la = ((AssemblyTreeNode)node).LoadedAssembly;
|
||||
la.AssemblyList.ReloadAssembly(la.FileName);
|
||||
}
|
||||
}
|
||||
MainWindow.Instance.SelectNodes(paths.Select(p => MainWindow.Instance.FindNodeByPath(p, true)).ToArray());
|
||||
MainWindow.Instance.RefreshDecompiledView();
|
||||
MainWindow.Instance.AssemblyTreeModel.SelectNodes(paths.Select(p => MainWindow.Instance.AssemblyTreeModel.FindNodeByPath(p, true)).ToArray());
|
||||
MainWindow.Instance.AssemblyTreeModel.RefreshDecompiledView();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -676,7 +676,7 @@ namespace ICSharpCode.ILSpy.TreeNodes
|
||||
}
|
||||
}
|
||||
await Task.WhenAll(tasks);
|
||||
MainWindow.Instance.RefreshDecompiledView();
|
||||
MainWindow.Instance.AssemblyTreeModel.RefreshDecompiledView();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -711,7 +711,7 @@ namespace ICSharpCode.ILSpy.TreeNodes
|
||||
node.RaisePropertyChanged(nameof(ILSpyTreeNode.IsAutoLoaded));
|
||||
}
|
||||
}
|
||||
MainWindow.Instance.CurrentAssemblyList.RefreshSave();
|
||||
MainWindow.Instance.AssemblyTreeModel.CurrentAssemblyList.RefreshSave();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -27,7 +27,6 @@ using System.Windows.Threading;
|
||||
|
||||
using ICSharpCode.Decompiler;
|
||||
using ICSharpCode.Decompiler.TypeSystem;
|
||||
using ICSharpCode.ILSpy.Util;
|
||||
using ICSharpCode.ILSpyX.Abstractions;
|
||||
using ICSharpCode.ILSpyX.TreeView.PlatformAbstractions;
|
||||
using ICSharpCode.ILSpyX.TreeView;
|
||||
@@ -72,8 +71,8 @@ namespace ICSharpCode.ILSpy.TreeNodes
|
||||
|
||||
public override void ActivateItemSecondary(IPlatformRoutedEventArgs e)
|
||||
{
|
||||
MainWindow.Instance.SelectNode(this, inNewTabPage: true);
|
||||
MainWindow.Instance.Dispatcher.BeginInvoke(DispatcherPriority.Background, (Action)MainWindow.Instance.RefreshDecompiledView);
|
||||
MainWindow.Instance.AssemblyTreeModel.SelectNode(this, inNewTabPage: true);
|
||||
MainWindow.Instance.Dispatcher.BeginInvoke(DispatcherPriority.Background, (Action)MainWindow.Instance.AssemblyTreeModel.RefreshDecompiledView);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
|
||||
@@ -57,4 +57,13 @@ namespace ICSharpCode.ILSpy.Util
|
||||
public class SessionSettingsChangedEventArgs(PropertyChangedEventArgs e) : WrappedEventArgs<PropertyChangedEventArgs>(e);
|
||||
|
||||
public class DockWorkspaceActiveTabPageChangedEventArgs : EventArgs;
|
||||
|
||||
public class NavigateToReferenceEventArgs(object reference, bool inNewTabPage = false) : EventArgs
|
||||
{
|
||||
public object Reference { get; } = reference;
|
||||
|
||||
public bool InNewTabPage { get; } = inNewTabPage;
|
||||
}
|
||||
|
||||
public class AssemblyTreeSelectionChangedEventArgs() : EventArgs;
|
||||
}
|
||||
@@ -0,0 +1,48 @@
|
||||
using System;
|
||||
|
||||
namespace ICSharpCode.ILSpy.Util
|
||||
{
|
||||
public class NavigationHistoryService
|
||||
{
|
||||
readonly NavigationHistory<NavigationState> history = new();
|
||||
|
||||
public static NavigationHistoryService Instance { get; } = new();
|
||||
|
||||
public bool CanNavigateBack => history.CanNavigateBack;
|
||||
public bool CanNavigateForward => history.CanNavigateForward;
|
||||
|
||||
private NavigationHistoryService()
|
||||
{
|
||||
}
|
||||
|
||||
public void UpdateCurrent(NavigationState navigationState)
|
||||
{
|
||||
history.UpdateCurrent(navigationState);
|
||||
}
|
||||
|
||||
public void Record(NavigationState navigationState)
|
||||
{
|
||||
history.Record(navigationState);
|
||||
}
|
||||
|
||||
public NavigationState GoForward()
|
||||
{
|
||||
return history.GoForward();
|
||||
}
|
||||
|
||||
public NavigationState GoBack()
|
||||
{
|
||||
return history.GoBack();
|
||||
}
|
||||
|
||||
public void Clear()
|
||||
{
|
||||
history.Clear();
|
||||
}
|
||||
|
||||
public void RemoveAll(Predicate<NavigationState> predicate)
|
||||
{
|
||||
history.RemoveAll(predicate);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,41 +0,0 @@
|
||||
// Copyright (c) 2019 AlphaSierraPapa for the SharpDevelop Team
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a copy of this
|
||||
// software and associated documentation files (the "Software"), to deal in the Software
|
||||
// without restriction, including without limitation the rights to use, copy, modify, merge,
|
||||
// publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons
|
||||
// to whom the Software is furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in all copies or
|
||||
// substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED,
|
||||
// INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
|
||||
// PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE
|
||||
// FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR
|
||||
// OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
|
||||
using System.ComponentModel.Composition;
|
||||
using System.Windows;
|
||||
using System.Windows.Input;
|
||||
|
||||
using ICSharpCode.ILSpy.Properties;
|
||||
|
||||
namespace ICSharpCode.ILSpy.ViewModels
|
||||
{
|
||||
[ExportToolPane]
|
||||
[PartCreationPolicy(CreationPolicy.Shared)]
|
||||
public class AssemblyListPaneModel : ToolPaneModel
|
||||
{
|
||||
public const string PaneContentId = "assemblyListPane";
|
||||
|
||||
public AssemblyListPaneModel()
|
||||
{
|
||||
Title = Resources.Assemblies;
|
||||
ContentId = PaneContentId;
|
||||
IsCloseable = false;
|
||||
ShortcutKey = new KeyGesture(Key.F6);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -27,7 +27,6 @@ using System.Windows.Input;
|
||||
using ICSharpCode.Decompiler.Metadata;
|
||||
using ICSharpCode.ILSpy.Commands;
|
||||
using ICSharpCode.ILSpy.Properties;
|
||||
using ICSharpCode.ILSpy.Util;
|
||||
using ICSharpCode.ILSpyX;
|
||||
|
||||
namespace ICSharpCode.ILSpy.ViewModels
|
||||
|
||||
@@ -21,7 +21,7 @@ using System.ComponentModel;
|
||||
using System.Windows;
|
||||
using System.Windows.Input;
|
||||
|
||||
using ICSharpCode.ILSpy.Docking;
|
||||
using ICSharpCode.Decompiler.IL;
|
||||
|
||||
using TomsToolbox.Wpf;
|
||||
|
||||
@@ -29,6 +29,13 @@ namespace ICSharpCode.ILSpy.ViewModels
|
||||
{
|
||||
public abstract class PaneModel : ObservableObject
|
||||
{
|
||||
private Throttle titleChangeThrottle;
|
||||
|
||||
protected PaneModel()
|
||||
{
|
||||
titleChangeThrottle = new Throttle(() => OnPropertyChanged(nameof(Title)));
|
||||
}
|
||||
|
||||
class CloseCommandImpl : ICommand
|
||||
{
|
||||
readonly PaneModel model;
|
||||
@@ -107,7 +114,10 @@ namespace ICSharpCode.ILSpy.ViewModels
|
||||
|
||||
public string Title {
|
||||
get => title;
|
||||
set => SetProperty(ref title, value);
|
||||
set {
|
||||
title = value;
|
||||
titleChangeThrottle.Tick();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -20,8 +20,6 @@ using System;
|
||||
using System.Threading.Tasks;
|
||||
|
||||
using ICSharpCode.ILSpy.TextView;
|
||||
using ICSharpCode.ILSpy.Util;
|
||||
using ICSharpCode.ILSpyX;
|
||||
|
||||
namespace ICSharpCode.ILSpy.ViewModels
|
||||
{
|
||||
|
||||
@@ -8,7 +8,6 @@ using System.Windows.Input;
|
||||
using ICSharpCode.Decompiler.IL;
|
||||
using ICSharpCode.Decompiler.IL.Transforms;
|
||||
using ICSharpCode.ILSpy.Docking;
|
||||
using ICSharpCode.ILSpy.Util;
|
||||
using ICSharpCode.ILSpy.ViewModels;
|
||||
|
||||
using TomsToolbox.Wpf.Composition.Mef;
|
||||
@@ -35,8 +34,8 @@ namespace ICSharpCode.ILSpy
|
||||
|
||||
#if DEBUG
|
||||
MessageBus<LanguageSettingsChangedEventArgs>.Subscribers += (sender, e) => LanguageSettings_PropertyChanged(sender, e);
|
||||
MessageBus<AssemblyTreeSelectionChangedEventArgs>.Subscribers += SelectionChanged;
|
||||
|
||||
MainWindow.Instance.SelectionChanged += SelectionChanged;
|
||||
writingOptions.PropertyChanged += WritingOptions_PropertyChanged;
|
||||
|
||||
if (SettingsService.Instance.SessionSettings.LanguageSettings.Language is ILAstLanguage l)
|
||||
@@ -53,7 +52,7 @@ namespace ICSharpCode.ILSpy
|
||||
DecompileAsync(lastSelectedStep);
|
||||
}
|
||||
|
||||
private void SelectionChanged(object sender, SelectionChangedEventArgs e)
|
||||
private void SelectionChanged(object sender, EventArgs e)
|
||||
{
|
||||
Dispatcher.Invoke(() => {
|
||||
tree.ItemsSource = null;
|
||||
@@ -123,8 +122,8 @@ namespace ICSharpCode.ILSpy
|
||||
lastSelectedStep = step;
|
||||
var window = MainWindow.Instance;
|
||||
var state = DockWorkspace.Instance.ActiveTabPage.GetState();
|
||||
DockWorkspace.Instance.ActiveTabPage.ShowTextViewAsync(textView => textView.DecompileAsync(window.CurrentLanguage, window.SelectedNodes,
|
||||
new DecompilationOptions(window.CurrentLanguageVersion, SettingsService.Instance.DecompilerSettings, SettingsService.Instance.DisplaySettings) {
|
||||
DockWorkspace.Instance.ActiveTabPage.ShowTextViewAsync(textView => textView.DecompileAsync(window.AssemblyTreeModel.CurrentLanguage, window.AssemblyTreeModel.SelectedNodes,
|
||||
new DecompilationOptions(window.AssemblyTreeModel.CurrentLanguageVersion, SettingsService.Instance.DecompilerSettings, SettingsService.Instance.DisplaySettings) {
|
||||
StepLimit = step,
|
||||
IsDebug = isDebug,
|
||||
TextViewState = state as TextView.DecompilerTextViewState
|
||||
|
||||
@@ -23,7 +23,7 @@ namespace TestPlugin
|
||||
{
|
||||
public override void Execute(object parameter)
|
||||
{
|
||||
foreach (var loadedAssembly in MainWindow.Instance.CurrentAssemblyList.GetAssemblies())
|
||||
foreach (var loadedAssembly in MainWindow.Instance.AssemblyTreeModel.CurrentAssemblyList.GetAssemblies())
|
||||
{
|
||||
loadedAssembly.AssemblyList.Unload(loadedAssembly);
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user