Browse Source

ILSpyX: remove InternalsVisibleTo for ILSpy + remove some redundant code.

pull/3274/head
tom-englert 10 months ago committed by tom-englert
parent
commit
152f70e789
  1. 4
      ICSharpCode.ILSpyX/AssemblyList.cs
  2. 2
      ICSharpCode.ILSpyX/Extensions/CollectionExtensions.cs
  3. 1
      ICSharpCode.ILSpyX/ICSharpCode.ILSpyX.csproj
  4. 8
      ICSharpCode.ILSpyX/LoadedPackage.cs
  5. 6
      ICSharpCode.ILSpyX/PdbProvider/PortableDebugInfoProvider.cs
  6. 6
      ICSharpCode.ILSpyX/TreeView/SharpTreeNode.cs
  7. 2
      ICSharpCode.ILSpyX/TreeView/TreeFlattener.cs
  8. 2
      ILSpy/Analyzers/AnalyzerSearchTreeNode.cs
  9. 46
      ILSpy/AssemblyTree/AssemblyListPane.xaml
  10. 162
      ILSpy/AssemblyTree/AssemblyListPaneModel.cs
  11. 2
      ILSpy/Commands/DecompileAllCommand.cs
  12. 5
      ILSpy/Commands/DecompileInNewViewCommand.cs
  13. 2
      ILSpy/Commands/DisassembleAllCommand.cs
  14. 8
      ILSpy/Commands/RemoveAssembliesWithLoadErrors.cs
  15. 30
      ILSpy/Docking/DockWorkspace.cs
  16. 16
      ILSpy/ExtensionMethods.cs
  17. 2
      ILSpy/Languages/CSharpLanguage.cs
  18. 2
      ILSpy/MainWindow.xaml.cs
  19. 2
      ILSpy/Metadata/CoffHeaderTreeNode.cs
  20. 2
      ILSpy/Metadata/OptionalHeaderTreeNode.cs
  21. 2
      ILSpy/Search/SearchPane.xaml.cs
  22. 4
      ILSpy/TextView/DecompilerTextView.cs
  23. 1
      ILSpy/TreeNodes/AssemblyListTreeNode.cs
  24. 2
      ILSpy/TreeNodes/AssemblyTreeNode.cs
  25. 2
      ILSpy/TreeNodes/ILSpyTreeNode.cs
  26. 10
      ILSpy/Util/MessageBus.cs
  27. 2
      ILSpy/Views/OpenFromGacDialog.xaml.cs
  28. 2
      TestPlugin/MainMenuCommand.cs

4
ICSharpCode.ILSpyX/AssemblyList.cs

@ -186,7 +186,7 @@ namespace ICSharpCode.ILSpyX
get { return listName; } get { return listName; }
} }
internal void Move(LoadedAssembly[] assembliesToMove, int index) public void Move(LoadedAssembly[] assembliesToMove, int index)
{ {
VerifyAccess(); VerifyAccess();
lock (lockObj) lock (lockObj)
@ -230,7 +230,7 @@ namespace ICSharpCode.ILSpyX
} }
} }
internal void RefreshSave() public void RefreshSave()
{ {
// Whenever the assembly list is modified, mark it as dirty // Whenever the assembly list is modified, mark it as dirty
// and enqueue a task that saves it once the UI has finished modifying the assembly list. // and enqueue a task that saves it once the UI has finished modifying the assembly list.

2
ICSharpCode.ILSpyX/Extensions/CollectionExtensions.cs

@ -27,7 +27,7 @@ namespace ICSharpCode.ILSpyX.Extensions
{ {
public static class CollectionExtensions public static class CollectionExtensions
{ {
public static void AddRange<T>(this ICollection<T> list, IEnumerable<T> items) internal static void AddRange<T>(this ICollection<T> list, IEnumerable<T> items)
{ {
foreach (T item in items) foreach (T item in items)
if (!list.Contains(item)) if (!list.Contains(item))

1
ICSharpCode.ILSpyX/ICSharpCode.ILSpyX.csproj

@ -41,7 +41,6 @@
</PropertyGroup> </PropertyGroup>
<ItemGroup> <ItemGroup>
<InternalsVisibleTo Include="ILSpy" Key="00240000048000009400000006020000002400005253413100040000010001004dcf3979c4e902efa4dd2163a039701ed5822e6f1134d77737296abbb97bf0803083cfb2117b4f5446a217782f5c7c634f9fe1fc60b4c11d62c5b3d33545036706296d31903ddcf750875db38a8ac379512f51620bb948c94d0831125fbc5fe63707cbb93f48c1459c4d1749eb7ac5e681a2f0d6d7c60fa527a3c0b8f92b02bf" />
<InternalsVisibleTo Include="ILSpy.Tests" Key="00240000048000009400000006020000002400005253413100040000010001004dcf3979c4e902efa4dd2163a039701ed5822e6f1134d77737296abbb97bf0803083cfb2117b4f5446a217782f5c7c634f9fe1fc60b4c11d62c5b3d33545036706296d31903ddcf750875db38a8ac379512f51620bb948c94d0831125fbc5fe63707cbb93f48c1459c4d1749eb7ac5e681a2f0d6d7c60fa527a3c0b8f92b02bf" /> <InternalsVisibleTo Include="ILSpy.Tests" Key="00240000048000009400000006020000002400005253413100040000010001004dcf3979c4e902efa4dd2163a039701ed5822e6f1134d77737296abbb97bf0803083cfb2117b4f5446a217782f5c7c634f9fe1fc60b4c11d62c5b3d33545036706296d31903ddcf750875db38a8ac379512f51620bb948c94d0831125fbc5fe63707cbb93f48c1459c4d1749eb7ac5e681a2f0d6d7c60fa527a3c0b8f92b02bf" />
</ItemGroup> </ItemGroup>

8
ICSharpCode.ILSpyX/LoadedPackage.cs

@ -51,14 +51,14 @@ namespace ICSharpCode.ILSpyX
public PackageKind Kind { get; } public PackageKind Kind { get; }
internal SingleFileBundle.Header BundleHeader { get; set; } public SingleFileBundle.Header BundleHeader { get; set; }
/// <summary> /// <summary>
/// List of all entries, including those in sub-directories within the package. /// List of all entries, including those in sub-directories within the package.
/// </summary> /// </summary>
public IReadOnlyList<PackageEntry> Entries { get; } public IReadOnlyList<PackageEntry> Entries { get; }
internal PackageFolder RootFolder { get; } public PackageFolder RootFolder { get; }
public LoadedPackage(PackageKind kind, IEnumerable<PackageEntry> entries) public LoadedPackage(PackageKind kind, IEnumerable<PackageEntry> entries)
{ {
@ -256,7 +256,7 @@ namespace ICSharpCode.ILSpyX
public abstract string FullName { get; } public abstract string FullName { get; }
} }
sealed class PackageFolder : IAssemblyResolver public sealed class PackageFolder : IAssemblyResolver
{ {
/// <summary> /// <summary>
/// Gets the short name of the folder. /// Gets the short name of the folder.
@ -326,7 +326,7 @@ namespace ICSharpCode.ILSpyX
readonly Dictionary<string, LoadedAssembly?> assemblies = new Dictionary<string, LoadedAssembly?>(StringComparer.OrdinalIgnoreCase); readonly Dictionary<string, LoadedAssembly?> assemblies = new Dictionary<string, LoadedAssembly?>(StringComparer.OrdinalIgnoreCase);
internal LoadedAssembly? ResolveFileName(string name) public LoadedAssembly? ResolveFileName(string name)
{ {
if (package.LoadedAssembly == null) if (package.LoadedAssembly == null)
return null; return null;

6
ICSharpCode.ILSpyX/PdbProvider/PortableDebugInfoProvider.cs

@ -32,7 +32,7 @@ using static ICSharpCode.Decompiler.Metadata.MetadataFile;
namespace ICSharpCode.ILSpyX.PdbProvider namespace ICSharpCode.ILSpyX.PdbProvider
{ {
class PortableDebugInfoProvider : IDebugInfoProvider public class PortableDebugInfoProvider : IDebugInfoProvider
{ {
string? pdbFileName; string? pdbFileName;
string moduleFileName; string moduleFileName;
@ -40,7 +40,7 @@ namespace ICSharpCode.ILSpyX.PdbProvider
MetadataReaderOptions options; MetadataReaderOptions options;
bool hasError; bool hasError;
internal bool IsEmbedded => pdbFileName == null; public bool IsEmbedded => pdbFileName == null;
public PortableDebugInfoProvider(string moduleFileName, MetadataReaderProvider provider, public PortableDebugInfoProvider(string moduleFileName, MetadataReaderProvider provider,
MetadataReaderOptions options = MetadataReaderOptions.Default, MetadataReaderOptions options = MetadataReaderOptions.Default,
@ -69,7 +69,7 @@ namespace ICSharpCode.ILSpyX.PdbProvider
} }
} }
internal MetadataReader? GetMetadataReader() public MetadataReader? GetMetadataReader()
{ {
try try
{ {

6
ICSharpCode.ILSpyX/TreeView/SharpTreeNode.cs

@ -182,7 +182,7 @@ namespace ICSharpCode.ILSpyX.TreeView
#endregion #endregion
#region OnChildrenChanged #region OnChildrenChanged
protected internal virtual void OnChildrenChanged(NotifyCollectionChangedEventArgs e) public virtual void OnChildrenChanged(NotifyCollectionChangedEventArgs e)
{ {
if (e.OldItems != null) if (e.OldItems != null)
{ {
@ -359,7 +359,7 @@ namespace ICSharpCode.ILSpyX.TreeView
return TreeTraversal.PreOrder(this.Children.Where(c => c.isVisible), n => n.Children.Where(c => c.isVisible)); return TreeTraversal.PreOrder(this.Children.Where(c => c.isVisible), n => n.Children.Where(c => c.isVisible));
} }
internal IEnumerable<SharpTreeNode> VisibleDescendantsAndSelf() public IEnumerable<SharpTreeNode> VisibleDescendantsAndSelf()
{ {
return TreeTraversal.PreOrder(this, n => n.Children.Where(c => c.isVisible)); return TreeTraversal.PreOrder(this, n => n.Children.Where(c => c.isVisible));
} }
@ -637,7 +637,7 @@ namespace ICSharpCode.ILSpyX.TreeView
return false; return false;
} }
internal void InternalDrop(IPlatformDragEventArgs e, int index) public void InternalDrop(IPlatformDragEventArgs e, int index)
{ {
if (LazyLoading) if (LazyLoading)
{ {

2
ICSharpCode.ILSpyX/TreeView/TreeFlattener.cs

@ -26,7 +26,7 @@ using System.Diagnostics;
namespace ICSharpCode.ILSpyX.TreeView namespace ICSharpCode.ILSpyX.TreeView
{ {
sealed class TreeFlattener : IList, INotifyCollectionChanged public sealed class TreeFlattener : IList, INotifyCollectionChanged
{ {
/// <summary> /// <summary>
/// The root node of the flat list tree. /// The root node of the flat list tree.

2
ILSpy/Analyzers/AnalyzerSearchTreeNode.cs

@ -61,7 +61,7 @@ namespace ICSharpCode.ILSpy.Analyzers
var context = new AnalyzerContext() { var context = new AnalyzerContext() {
CancellationToken = ct, CancellationToken = ct,
Language = Language, Language = Language,
AssemblyList = MainWindow.Instance.AssemblyTreeModel.CurrentAssemblyList AssemblyList = MainWindow.Instance.AssemblyTreeModel.AssemblyList
}; };
var results = analyzer.Analyze(symbol, context).Select(SymbolTreeNodeFactory); var results = analyzer.Analyze(symbol, context).Select(SymbolTreeNodeFactory);
if (context.SortResults) if (context.SortResults)

46
ILSpy/AssemblyTree/AssemblyListPane.xaml

@ -1,28 +1,28 @@
<treeView:SharpTreeView x:Class="ICSharpCode.ILSpy.AssemblyTree.AssemblyListPane" <treeView:SharpTreeView x:Class="ICSharpCode.ILSpy.AssemblyTree.AssemblyListPane"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008" xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:treeView="clr-namespace:ICSharpCode.ILSpy.Controls.TreeView" xmlns:treeView="clr-namespace:ICSharpCode.ILSpy.Controls.TreeView"
xmlns:treeNodes="clr-namespace:ICSharpCode.ILSpy.TreeNodes" xmlns:treeNodes="clr-namespace:ICSharpCode.ILSpy.TreeNodes"
xmlns:assemblyTree="clr-namespace:ICSharpCode.ILSpy.AssemblyTree" xmlns:assemblyTree="clr-namespace:ICSharpCode.ILSpy.AssemblyTree"
xmlns:toms="urn:TomsToolbox" xmlns:toms="urn:TomsToolbox"
mc:Ignorable="d" d:DesignHeight="450" d:DesignWidth="800" mc:Ignorable="d" d:DesignHeight="450" d:DesignWidth="800"
d:DataContext="{d:DesignInstance assemblyTree:AssemblyListPaneModel}" d:DataContext="{d:DesignInstance assemblyTree:AssemblyListPaneModel}"
AutomationProperties.Name="Assemblies and Classes" AutomationProperties.Name="Assemblies and Classes"
ShowRoot="False" ShowRoot="False"
AllowDropOrder="True" AllowDropOrder="True"
AllowDrop="True" AllowDrop="True"
BorderThickness="0" Visibility="Visible" BorderThickness="0" Visibility="Visible"
Root="{Binding Root}" Root="{Binding Root}"
SelectedItem="{Binding SelectedItem, Mode=TwoWay}" SelectedItem="{Binding SelectedItem, Mode=TwoWay}"
toms:MultiSelectorExtensions.SelectionBinding="{Binding SelectedItems}"> toms:MultiSelectorExtensions.SelectionBinding="{Binding SelectedItems}">
<treeView:SharpTreeView.ItemContainerStyle> <treeView:SharpTreeView.ItemContainerStyle>
<Style TargetType="treeView:SharpTreeViewItem"> <Style TargetType="treeView:SharpTreeViewItem">
<Setter Property="Template"> <Setter Property="Template">
<Setter.Value> <Setter.Value>
<ControlTemplate TargetType="{x:Type treeView:SharpTreeViewItem}" <ControlTemplate TargetType="{x:Type treeView:SharpTreeViewItem}"
d:DataContext="{d:DesignInstance treeNodes:ILSpyTreeNode}"> d:DataContext="{d:DesignInstance treeNodes:ILSpyTreeNode}">
<Border Background="Transparent"> <Border Background="Transparent">
<Border Background="{TemplateBinding Background}"> <Border Background="{TemplateBinding Background}">
<treeView:SharpTreeNodeView x:Name="nodeView" HorizontalAlignment="Left" /> <treeView:SharpTreeNodeView x:Name="nodeView" HorizontalAlignment="Left" />
@ -37,13 +37,13 @@
</DataTrigger> </DataTrigger>
<Trigger Property="IsSelected" Value="True"> <Trigger Property="IsSelected" Value="True">
<Setter TargetName="nodeView" Property="TextBackground" <Setter TargetName="nodeView" Property="TextBackground"
Value="{DynamicResource {x:Static SystemColors.HighlightBrushKey}}" /> Value="{DynamicResource {x:Static SystemColors.HighlightBrushKey}}" />
<Setter TargetName="nodeView" Property="Foreground" <Setter TargetName="nodeView" Property="Foreground"
Value="{DynamicResource {x:Static SystemColors.HighlightTextBrushKey}}" /> Value="{DynamicResource {x:Static SystemColors.HighlightTextBrushKey}}" />
</Trigger> </Trigger>
<Trigger Property="IsEnabled" Value="False"> <Trigger Property="IsEnabled" Value="False">
<Setter TargetName="nodeView" Property="Foreground" <Setter TargetName="nodeView" Property="Foreground"
Value="{DynamicResource {x:Static SystemColors.GrayTextBrushKey}}" /> Value="{DynamicResource {x:Static SystemColors.GrayTextBrushKey}}" />
</Trigger> </Trigger>
</ControlTemplate.Triggers> </ControlTemplate.Triggers>
</ControlTemplate> </ControlTemplate>
@ -51,4 +51,4 @@
</Setter> </Setter>
</Style> </Style>
</treeView:SharpTreeView.ItemContainerStyle> </treeView:SharpTreeView.ItemContainerStyle>
</treeView:SharpTreeView> </treeView:SharpTreeView>

162
ILSpy/AssemblyTree/AssemblyListPaneModel.cs

@ -36,7 +36,6 @@ using ICSharpCode.ILSpyX.Settings;
using ICSharpCode.ILSpyX.TreeView; using ICSharpCode.ILSpyX.TreeView;
using System.Collections.Specialized; using System.Collections.Specialized;
using System.ComponentModel; using System.ComponentModel;
using System.Diagnostics;
using System.Linq; using System.Linq;
using ICSharpCode.Decompiler.Metadata; using ICSharpCode.Decompiler.Metadata;
@ -52,6 +51,7 @@ using ICSharpCode.ILSpy.Search;
using ICSharpCode.Decompiler; using ICSharpCode.Decompiler;
using System.Text; using System.Text;
using TomsToolbox.Essentials;
using TomsToolbox.Wpf; using TomsToolbox.Wpf;
namespace ICSharpCode.ILSpy.AssemblyTree namespace ICSharpCode.ILSpy.AssemblyTree
@ -64,12 +64,8 @@ namespace ICSharpCode.ILSpy.AssemblyTree
public const string PaneContentId = "assemblyListPane"; public const string PaneContentId = "assemblyListPane";
AssemblyListPane activeView; AssemblyListPane activeView;
AssemblyList assemblyList;
AssemblyListTreeNode assemblyListTreeNode; AssemblyListTreeNode assemblyListTreeNode;
bool refreshInProgress;
bool changingActiveTab;
readonly NavigationHistoryService history = NavigationHistoryService.Instance; readonly NavigationHistoryService history = NavigationHistoryService.Instance;
public AssemblyListPaneModel() public AssemblyListPaneModel()
@ -107,9 +103,7 @@ namespace ICSharpCode.ILSpy.AssemblyTree
} }
} }
public AssemblyList CurrentAssemblyList { public AssemblyList AssemblyList { get; private set; }
get { return assemblyList; }
}
private SharpTreeNode root; private SharpTreeNode root;
public SharpTreeNode Root { public SharpTreeNode Root {
@ -230,7 +224,7 @@ namespace ICSharpCode.ILSpy.AssemblyTree
SharpTreeNode node = null; SharpTreeNode node = null;
if (activeTreeViewPath?.Length > 0) if (activeTreeViewPath?.Length > 0)
{ {
foreach (var asm in CurrentAssemblyList.GetAssemblies()) foreach (var asm in AssemblyList.GetAssemblies())
{ {
if (asm.FileName == activeTreeViewPath[0]) if (asm.FileName == activeTreeViewPath[0])
{ {
@ -327,37 +321,37 @@ namespace ICSharpCode.ILSpy.AssemblyTree
if (loadPreviousAssemblies) if (loadPreviousAssemblies)
{ {
this.assemblyList = SettingsService.Instance.AssemblyListManager.LoadList(sessionSettings.ActiveAssemblyList); this.AssemblyList = SettingsService.Instance.AssemblyListManager.LoadList(sessionSettings.ActiveAssemblyList);
} }
else else
{ {
SettingsService.Instance.AssemblyListManager.ClearAll(); SettingsService.Instance.AssemblyListManager.ClearAll();
this.assemblyList = SettingsService.Instance.AssemblyListManager.CreateList(AssemblyListManager.DefaultListName); this.AssemblyList = SettingsService.Instance.AssemblyListManager.CreateList(AssemblyListManager.DefaultListName);
} }
HandleCommandLineArguments(App.CommandLineArguments); HandleCommandLineArguments(App.CommandLineArguments);
if (assemblyList.GetAssemblies().Length == 0 if (AssemblyList.GetAssemblies().Length == 0
&& assemblyList.ListName == AssemblyListManager.DefaultListName && AssemblyList.ListName == AssemblyListManager.DefaultListName
&& loadPreviousAssemblies) && loadPreviousAssemblies)
{ {
LoadInitialAssemblies(); LoadInitialAssemblies();
} }
ShowAssemblyList(this.assemblyList); ShowAssemblyList(this.AssemblyList);
if (sessionSettings.ActiveAutoLoadedAssembly != null if (sessionSettings.ActiveAutoLoadedAssembly != null
&& File.Exists(sessionSettings.ActiveAutoLoadedAssembly)) && File.Exists(sessionSettings.ActiveAutoLoadedAssembly))
{ {
this.assemblyList.Open(sessionSettings.ActiveAutoLoadedAssembly, true); this.AssemblyList.Open(sessionSettings.ActiveAutoLoadedAssembly, true);
} }
Dispatcher.BeginInvoke(DispatcherPriority.Loaded, new Action(() => OpenAssemblies(SettingsService.Instance.SpySettings))); Dispatcher.BeginInvoke(DispatcherPriority.Loaded, OpenAssemblies);
} }
void OpenAssemblies(ILSpySettings spySettings) void OpenAssemblies()
{ {
HandleCommandLineArgumentsAfterShowList(App.CommandLineArguments, spySettings); HandleCommandLineArgumentsAfterShowList(App.CommandLineArguments, SettingsService.Instance.SpySettings);
AvalonEditTextOutput output = new(); AvalonEditTextOutput output = new();
if (FormatExceptions(App.StartupExceptions.ToArray(), output)) if (FormatExceptions(App.StartupExceptions.ToArray(), output))
@ -379,7 +373,7 @@ namespace ICSharpCode.ILSpy.AssemblyTree
{ {
AssemblyList list = SettingsService.Instance.AssemblyListManager.LoadList(name); AssemblyList list = SettingsService.Instance.AssemblyListManager.LoadList(name);
//Only load a new list when it is a different one //Only load a new list when it is a different one
if (list.ListName != CurrentAssemblyList.ListName) if (list.ListName != AssemblyList.ListName)
{ {
ShowAssemblyList(list); ShowAssemblyList(list);
SelectNode(Root); SelectNode(Root);
@ -389,12 +383,12 @@ namespace ICSharpCode.ILSpy.AssemblyTree
void ShowAssemblyList(AssemblyList assemblyList) void ShowAssemblyList(AssemblyList assemblyList)
{ {
history.Clear(); history.Clear();
if (this.assemblyList != null) if (this.AssemblyList != null)
{ {
this.assemblyList.CollectionChanged -= assemblyList_CollectionChanged; this.AssemblyList.CollectionChanged -= assemblyList_CollectionChanged;
} }
this.assemblyList = assemblyList; this.AssemblyList = assemblyList;
assemblyList.CollectionChanged += assemblyList_CollectionChanged; assemblyList.CollectionChanged += assemblyList_CollectionChanged;
@ -450,12 +444,12 @@ namespace ICSharpCode.ILSpy.AssemblyTree
typeof(System.Windows.FrameworkElement).Assembly typeof(System.Windows.FrameworkElement).Assembly
}; };
foreach (System.Reflection.Assembly asm in initialAssemblies) foreach (System.Reflection.Assembly asm in initialAssemblies)
assemblyList.OpenAssembly(asm.Location); AssemblyList.OpenAssembly(asm.Location);
} }
void LanguageSettings_PropertyChanged(object sender, PropertyChangedEventArgs e) void LanguageSettings_PropertyChanged(object sender, PropertyChangedEventArgs e)
{ {
if (e.PropertyName == "Language" || e.PropertyName == "LanguageVersion") if (e.PropertyName is nameof(LanguageSettings.Language) or nameof(LanguageSettings.LanguageVersion))
{ {
DecompileSelectedNodes(recordHistory: false); DecompileSelectedNodes(recordHistory: false);
} }
@ -496,18 +490,12 @@ namespace ICSharpCode.ILSpy.AssemblyTree
} }
} }
internal void SelectNodes(IEnumerable<SharpTreeNode> nodes, bool inNewTabPage = false, bool setFocus = true, bool changingTab = false, bool ignoreCompilationRequests = false) internal void SelectNodes(IEnumerable<SharpTreeNode> nodes, bool ignoreCompilationRequests = false)
{ {
this.ignoreDecompilationRequests = ignoreCompilationRequests; this.ignoreDecompilationRequests = ignoreCompilationRequests;
try try
{ {
if (inNewTabPage)
{
DockWorkspace.Instance.AddTabPage();
}
// Ensure nodes exist // Ensure nodes exist
var nodesList = nodes.Select(n => FindNodeByPath(GetPathForNode(n), true)) var nodesList = nodes.Select(n => FindNodeByPath(GetPathForNode(n), true))
.Where(n => n != null) .Where(n => n != null)
@ -518,28 +506,14 @@ namespace ICSharpCode.ILSpy.AssemblyTree
return; return;
} }
this.changingActiveTab = changingTab || inNewTabPage; if (SelectedItems.SequenceEqual(nodesList))
var currentFocused = Keyboard.FocusedElement;
try
{ {
if (SelectedItems.SequenceEqual(nodesList)) Dispatcher.BeginInvoke(RefreshDecompiledView);
{ return;
Dispatcher.BeginInvoke(RefreshDecompiledView);
return;
}
this.SelectedItems.Clear();
this.SelectedItems.AddRange(nodesList);
} }
finally
{
if (!setFocus)
currentFocused.Focus();
this.changingActiveTab = false; SelectedItems.Clear();
} SelectedItems.AddRange(nodesList);
} }
finally finally
{ {
@ -642,7 +616,7 @@ namespace ICSharpCode.ILSpy.AssemblyTree
break; break;
case EntityReference unresolvedEntity: case EntityReference unresolvedEntity:
string protocol = unresolvedEntity.Protocol; string protocol = unresolvedEntity.Protocol;
var file = unresolvedEntity.ResolveAssembly(assemblyList); var file = unresolvedEntity.ResolveAssembly(AssemblyList);
if (file == null) if (file == null)
{ {
break; break;
@ -681,35 +655,32 @@ namespace ICSharpCode.ILSpy.AssemblyTree
public void LoadAssemblies(IEnumerable<string> fileNames, List<LoadedAssembly> loadedAssemblies = null, bool focusNode = true) public void LoadAssemblies(IEnumerable<string> fileNames, List<LoadedAssembly> loadedAssemblies = null, bool focusNode = true)
{ {
var currentFocus = Keyboard.FocusedElement; using (Keyboard.FocusedElement.PreserveFocus(!focusNode))
AssemblyTreeNode lastNode = null;
foreach (string file in fileNames)
{ {
var assembly = assemblyList.OpenAssembly(file); AssemblyTreeNode lastNode = null;
if (loadedAssemblies != null) foreach (string file in fileNames)
{ {
loadedAssemblies.Add(assembly); var assembly = AssemblyList.OpenAssembly(file);
}
else if (loadedAssemblies != null)
{
var node = assemblyListTreeNode.FindAssemblyNode(assembly);
if (node != null && focusNode)
{ {
lastNode = node; loadedAssemblies.Add(assembly);
SelectedItems.Add(node); }
else
{
var node = assemblyListTreeNode.FindAssemblyNode(assembly);
if (node != null && focusNode)
{
lastNode = node;
SelectedItems.Add(node);
}
} }
} }
} if (focusNode && lastNode != null)
{
if (!focusNode) activeView?.FocusNode(lastNode);
{ }
currentFocus?.Focus();
}
else if (lastNode != null)
{
activeView?.FocusNode(lastNode);
} }
} }
@ -717,22 +688,11 @@ namespace ICSharpCode.ILSpy.AssemblyTree
void 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; var delayDecompilationRequestDueToContextMenu = Mouse.RightButton == MouseButtonState.Pressed;
if (!changingActiveTab && !delayDecompilationRequestDueToContextMenu) if (!delayDecompilationRequestDueToContextMenu)
{ {
DecompileSelectedNodes(state); DecompileSelectedNodes();
} }
else else
{ {
@ -763,9 +723,6 @@ namespace ICSharpCode.ILSpy.AssemblyTree
if (ignoreDecompilationRequests) if (ignoreDecompilationRequests)
return; return;
if (SelectedItems.Count == 0 && refreshInProgress)
return;
var activeTabPage = DockWorkspace.Instance.ActiveTabPage; var activeTabPage = DockWorkspace.Instance.ActiveTabPage;
if (recordHistory) if (recordHistory)
@ -788,6 +745,7 @@ namespace ICSharpCode.ILSpy.AssemblyTree
MainWindow.Instance.NavigateTo(new(newState.ViewedUri, null), recordHistory: false); MainWindow.Instance.NavigateTo(new(newState.ViewedUri, null), recordHistory: false);
return; return;
} }
var options = SettingsService.Instance.CreateDecompilationOptions(activeTabPage); var options = SettingsService.Instance.CreateDecompilationOptions(activeTabPage);
options.TextViewState = newState; options.TextViewState = newState;
activeTabPage.ShowTextViewAsync(textView => textView.DecompileAsync(this.CurrentLanguage, this.SelectedNodes, options)); activeTabPage.ShowTextViewAsync(textView => textView.DecompileAsync(this.CurrentLanguage, this.SelectedNodes, options));
@ -795,15 +753,7 @@ namespace ICSharpCode.ILSpy.AssemblyTree
public void RefreshDecompiledView() public void RefreshDecompiledView()
{ {
try DecompileSelectedNodes();
{
refreshInProgress = true;
DecompileSelectedNodes();
}
finally
{
refreshInProgress = false;
}
} }
public Language CurrentLanguage => SettingsService.Instance.SessionSettings.LanguageSettings.Language; public Language CurrentLanguage => SettingsService.Instance.SessionSettings.LanguageSettings.Language;
@ -821,20 +771,12 @@ namespace ICSharpCode.ILSpy.AssemblyTree
public void Refresh() public void Refresh()
{ {
var currentFocus = Keyboard.FocusedElement; using (Keyboard.FocusedElement.PreserveFocus())
try
{ {
refreshInProgress = true;
var path = GetPathForNode(SelectedItem); var path = GetPathForNode(SelectedItem);
ShowAssemblyList(SettingsService.Instance.AssemblyListManager.LoadList(assemblyList.ListName)); ShowAssemblyList(SettingsService.Instance.AssemblyListManager.LoadList(AssemblyList.ListName));
SelectNode(FindNodeByPath(path, true), inNewTabPage: false); SelectNode(FindNodeByPath(path, true), inNewTabPage: false);
} }
finally
{
refreshInProgress = false;
currentFocus?.Focus();
}
} }
public void UnselectAll(bool ignoreCompilationRequests = false) public void UnselectAll(bool ignoreCompilationRequests = false)
@ -861,7 +803,7 @@ namespace ICSharpCode.ILSpy.AssemblyTree
{ {
using (activeView?.LockUpdates()) using (activeView?.LockUpdates())
{ {
CurrentAssemblyList.Sort(AssemblyComparer.Instance); AssemblyList.Sort(AssemblyComparer.Instance);
} }
} }

2
ILSpy/Commands/DecompileAllCommand.cs

@ -49,7 +49,7 @@ namespace ICSharpCode.ILSpy
Docking.DockWorkspace.Instance.RunWithCancellation(ct => Task<AvalonEditTextOutput>.Factory.StartNew(() => { Docking.DockWorkspace.Instance.RunWithCancellation(ct => Task<AvalonEditTextOutput>.Factory.StartNew(() => {
AvalonEditTextOutput output = new AvalonEditTextOutput(); AvalonEditTextOutput output = new AvalonEditTextOutput();
Parallel.ForEach( Parallel.ForEach(
Partitioner.Create(MainWindow.Instance.AssemblyTreeModel.CurrentAssemblyList.GetAssemblies(), loadBalance: true), Partitioner.Create(MainWindow.Instance.AssemblyTreeModel.AssemblyList.GetAssemblies(), loadBalance: true),
new ParallelOptions { MaxDegreeOfParallelism = Environment.ProcessorCount, CancellationToken = ct }, new ParallelOptions { MaxDegreeOfParallelism = Environment.ProcessorCount, CancellationToken = ct },
delegate (LoadedAssembly asm) { delegate (LoadedAssembly asm) {
if (!asm.HasLoadError) if (!asm.HasLoadError)

5
ILSpy/Commands/DecompileInNewViewCommand.cs

@ -23,6 +23,7 @@ using System.Linq;
using System.Windows.Threading; using System.Windows.Threading;
using ICSharpCode.Decompiler.TypeSystem; using ICSharpCode.Decompiler.TypeSystem;
using ICSharpCode.ILSpy.Docking;
using ICSharpCode.ILSpy.Properties; using ICSharpCode.ILSpy.Properties;
using ICSharpCode.ILSpy.TreeNodes; using ICSharpCode.ILSpy.TreeNodes;
@ -84,7 +85,9 @@ namespace ICSharpCode.ILSpy.Commands
if (nodes.Length == 0) if (nodes.Length == 0)
return; return;
MainWindow.Instance.AssemblyTreeModel.SelectNodes(nodes, inNewTabPage: true); DockWorkspace.Instance.AddTabPage();
MainWindow.Instance.AssemblyTreeModel.SelectNodes(nodes);
} }
} }
} }

2
ILSpy/Commands/DisassembleAllCommand.cs

@ -45,7 +45,7 @@ namespace ICSharpCode.ILSpy
dockWorkspace.RunWithCancellation(ct => Task<AvalonEditTextOutput>.Factory.StartNew(() => { dockWorkspace.RunWithCancellation(ct => Task<AvalonEditTextOutput>.Factory.StartNew(() => {
AvalonEditTextOutput output = new(); AvalonEditTextOutput output = new();
Parallel.ForEach( Parallel.ForEach(
Partitioner.Create(MainWindow.Instance.AssemblyTreeModel.CurrentAssemblyList.GetAssemblies(), loadBalance: true), Partitioner.Create(MainWindow.Instance.AssemblyTreeModel.AssemblyList.GetAssemblies(), loadBalance: true),
new() { MaxDegreeOfParallelism = Environment.ProcessorCount, CancellationToken = ct }, new() { MaxDegreeOfParallelism = Environment.ProcessorCount, CancellationToken = ct },
asm => { asm => {
if (!asm.HasLoadError) if (!asm.HasLoadError)

8
ILSpy/Commands/RemoveAssembliesWithLoadErrors.cs

@ -29,12 +29,12 @@ namespace ICSharpCode.ILSpy
{ {
public override bool CanExecute(object parameter) public override bool CanExecute(object parameter)
{ {
return MainWindow.Instance.AssemblyTreeModel.CurrentAssemblyList?.GetAssemblies().Any(l => l.HasLoadError) == true; return MainWindow.Instance.AssemblyTreeModel.AssemblyList?.GetAssemblies().Any(l => l.HasLoadError) == true;
} }
public override void Execute(object parameter) public override void Execute(object parameter)
{ {
foreach (var asm in MainWindow.Instance.AssemblyTreeModel.CurrentAssemblyList.GetAssemblies()) foreach (var asm in MainWindow.Instance.AssemblyTreeModel.AssemblyList.GetAssemblies())
{ {
if (!asm.HasLoadError) if (!asm.HasLoadError)
continue; continue;
@ -51,12 +51,12 @@ namespace ICSharpCode.ILSpy
{ {
public override bool CanExecute(object parameter) public override bool CanExecute(object parameter)
{ {
return MainWindow.Instance.AssemblyTreeModel.CurrentAssemblyList?.Count > 0; return MainWindow.Instance.AssemblyTreeModel.AssemblyList?.Count > 0;
} }
public override void Execute(object parameter) public override void Execute(object parameter)
{ {
MainWindow.Instance.AssemblyTreeModel.CurrentAssemblyList?.Clear(); MainWindow.Instance.AssemblyTreeModel.AssemblyList?.Clear();
} }
} }
} }

30
ILSpy/Docking/DockWorkspace.cs

@ -17,7 +17,6 @@
// DEALINGS IN THE SOFTWARE. // DEALINGS IN THE SOFTWARE.
using System; using System;
using System.Collections.Generic;
using System.Collections.ObjectModel; using System.Collections.ObjectModel;
using System.Collections.Specialized; using System.Collections.Specialized;
using System.Linq; using System.Linq;
@ -38,6 +37,7 @@ using ICSharpCode.ILSpy.ViewModels;
using ICSharpCode.ILSpyX.Extensions; using ICSharpCode.ILSpyX.Extensions;
using TomsToolbox.Composition; using TomsToolbox.Composition;
using TomsToolbox.Essentials;
using TomsToolbox.Wpf; using TomsToolbox.Wpf;
namespace ICSharpCode.ILSpy.Docking namespace ICSharpCode.ILSpy.Docking
@ -71,20 +71,15 @@ namespace ICSharpCode.ILSpy.Docking
foreach (var tab in tabPages.ToArray()) foreach (var tab in tabPages.ToArray())
{ {
var state = tab.GetState(); var state = tab.GetState();
if (state == null || state.DecompiledNodes == null) var decompiledNodes = state?.DecompiledNodes;
{ if (decompiledNodes == null)
continue; continue;
}
bool found = false; bool found = decompiledNodes
foreach (var node in state.DecompiledNodes) .Select(node => node.Ancestors().OfType<TreeNodes.AssemblyTreeNode>().LastOrDefault())
{ .ExceptNullItems()
var assemblyNode = node.Ancestors().OfType<TreeNodes.AssemblyTreeNode>().LastOrDefault(); .Any(assemblyNode => !e.OldItems.Contains(assemblyNode.LoadedAssembly));
if (assemblyNode != null && !e.OldItems.Contains(assemblyNode.LoadedAssembly))
{
found = true;
break;
}
}
if (!found && tabPages.Count > 1) if (!found && tabPages.Count > 1)
{ {
tabPages.Remove(tab); tabPages.Remove(tab);
@ -156,22 +151,21 @@ namespace ICSharpCode.ILSpy.Docking
{ {
if (state.DecompiledNodes != null) if (state.DecompiledNodes != null)
{ {
MainWindow.Instance.AssemblyTreeModel.SelectNodes(state.DecompiledNodes, inNewTabPage: false, setFocus: true, changingTab: true); MainWindow.Instance.AssemblyTreeModel.SelectNodes(state.DecompiledNodes);
} }
else else
{ {
MainWindow.Instance.NavigateTo(new(state.ViewedUri, null)); MainWindow.Instance.NavigateTo(new(state.ViewedUri, null));
} }
} }
MessageBus.Send(this, new DockWorkspaceActiveTabPageChangedEventArgs());
} }
} }
public void InitializeLayout(DockingManager manager) public void InitializeLayout(DockingManager manager)
{ {
var toolPanes = exportProvider.GetExportedValues<ToolPaneModel>("ToolPane").OrderBy(item => item.Title); var panes = exportProvider.GetExportedValues<ToolPaneModel>("ToolPane").OrderBy(item => item.Title);
this.toolPanes.AddRange(toolPanes); this.toolPanes.AddRange(panes);
manager.LayoutUpdateStrategy = this; manager.LayoutUpdateStrategy = this;
XmlLayoutSerializer serializer = new XmlLayoutSerializer(manager); XmlLayoutSerializer serializer = new XmlLayoutSerializer(manager);

16
ILSpy/ExtensionMethods.cs

@ -195,5 +195,21 @@ namespace ICSharpCode.ILSpy
return true; return true;
} }
public static IDisposable PreserveFocus(this IInputElement? inputElement, bool preserve = true)
{
return new RestoreFocusHelper(inputElement, preserve);
}
private sealed class RestoreFocusHelper(IInputElement? inputElement, bool preserve) : IDisposable
{
public void Dispose()
{
if (preserve)
{
inputElement?.Focus();
}
}
}
} }
} }

2
ILSpy/Languages/CSharpLanguage.cs

@ -358,7 +358,7 @@ namespace ICSharpCode.ILSpy
void AddReferenceWarningMessage(MetadataFile module, ITextOutput output) void AddReferenceWarningMessage(MetadataFile module, ITextOutput output)
{ {
var loadedAssembly = MainWindow.Instance.AssemblyTreeModel.CurrentAssemblyList.GetAssemblies().FirstOrDefault(la => la.GetMetadataFileOrNull() == module); var loadedAssembly = MainWindow.Instance.AssemblyTreeModel.AssemblyList.GetAssemblies().FirstOrDefault(la => la.GetMetadataFileOrNull() == module);
if (loadedAssembly == null || !loadedAssembly.LoadedAssemblyReferencesInfo.HasErrors) if (loadedAssembly == null || !loadedAssembly.LoadedAssemblyReferencesInfo.HasErrors)
return; return;
string line1 = Properties.Resources.WarningSomeAssemblyReference; string line1 = Properties.Resources.WarningSomeAssemblyReference;

2
ILSpy/MainWindow.xaml.cs

@ -439,7 +439,7 @@ namespace ICSharpCode.ILSpy
base.OnClosing(e); base.OnClosing(e);
var sessionSettings = SettingsService.Instance.SessionSettings; var sessionSettings = SettingsService.Instance.SessionSettings;
sessionSettings.ActiveAssemblyList = AssemblyTreeModel.CurrentAssemblyList.ListName; sessionSettings.ActiveAssemblyList = AssemblyTreeModel.AssemblyList.ListName;
sessionSettings.ActiveTreeViewPath = AssemblyTreeModel.SelectedPath; sessionSettings.ActiveTreeViewPath = AssemblyTreeModel.SelectedPath;
sessionSettings.ActiveAutoLoadedAssembly = GetAutoLoadedAssemblyNode(AssemblyTreeModel.SelectedItem); sessionSettings.ActiveAutoLoadedAssembly = GetAutoLoadedAssemblyNode(AssemblyTreeModel.SelectedItem);
sessionSettings.WindowBounds = this.RestoreBounds; sessionSettings.WindowBounds = this.RestoreBounds;

2
ILSpy/Metadata/CoffHeaderTreeNode.cs

@ -28,6 +28,8 @@ using ICSharpCode.ILSpy.TreeNodes;
using ICSharpCode.ILSpy.ViewModels; using ICSharpCode.ILSpy.ViewModels;
using ICSharpCode.ILSpyX.Extensions; using ICSharpCode.ILSpyX.Extensions;
using TomsToolbox.Essentials;
namespace ICSharpCode.ILSpy.Metadata namespace ICSharpCode.ILSpy.Metadata
{ {
class CoffHeaderTreeNode : ILSpyTreeNode class CoffHeaderTreeNode : ILSpyTreeNode

2
ILSpy/Metadata/OptionalHeaderTreeNode.cs

@ -27,6 +27,8 @@ using ICSharpCode.Decompiler.Metadata;
using ICSharpCode.ILSpy.TreeNodes; using ICSharpCode.ILSpy.TreeNodes;
using ICSharpCode.ILSpyX.Extensions; using ICSharpCode.ILSpyX.Extensions;
using TomsToolbox.Essentials;
namespace ICSharpCode.ILSpy.Metadata namespace ICSharpCode.ILSpy.Metadata
{ {
class OptionalHeaderTreeNode : ILSpyTreeNode class OptionalHeaderTreeNode : ILSpyTreeNode

2
ILSpy/Search/SearchPane.xaml.cs

@ -249,7 +249,7 @@ namespace ICSharpCode.ILSpy.Search
{ {
searchProgressBar.IsIndeterminate = true; searchProgressBar.IsIndeterminate = true;
startedSearch = new(await mainWindow.AssemblyTreeModel.CurrentAssemblyList.GetAllAssemblies(), searchTerm, startedSearch = new(await mainWindow.AssemblyTreeModel.AssemblyList.GetAllAssemblies(), searchTerm,
(SearchMode)searchModeComboBox.SelectedIndex, mainWindow.AssemblyTreeModel.CurrentLanguage, (SearchMode)searchModeComboBox.SelectedIndex, mainWindow.AssemblyTreeModel.CurrentLanguage,
SettingsService.Instance.SessionSettings.LanguageSettings.ShowApiLevel); SettingsService.Instance.SessionSettings.LanguageSettings.ShowApiLevel);
currentSearch = startedSearch; currentSearch = startedSearch;

4
ILSpy/TextView/DecompilerTextView.cs

@ -414,7 +414,7 @@ namespace ICSharpCode.ILSpy.TextView
} }
else if (segment.Reference is EntityReference unresolvedEntity) else if (segment.Reference is EntityReference unresolvedEntity)
{ {
var module = unresolvedEntity.ResolveAssembly(MainWindow.Instance.AssemblyTreeModel.CurrentAssemblyList); var module = unresolvedEntity.ResolveAssembly(MainWindow.Instance.AssemblyTreeModel.AssemblyList);
if (module == null) if (module == null)
return null; return null;
var typeSystem = new DecompilerTypeSystem(module, var typeSystem = new DecompilerTypeSystem(module,
@ -474,7 +474,7 @@ namespace ICSharpCode.ILSpy.TextView
IEntity? ResolveReference(string idString) IEntity? ResolveReference(string idString)
{ {
return AssemblyListPaneModel.FindEntityInRelevantAssemblies(idString, MainWindow.Instance.AssemblyTreeModel.CurrentAssemblyList.GetAssemblies()); return AssemblyListPaneModel.FindEntityInRelevantAssemblies(idString, MainWindow.Instance.AssemblyTreeModel.AssemblyList.GetAssemblies());
} }
} }

1
ILSpy/TreeNodes/AssemblyListTreeNode.cs

@ -24,6 +24,7 @@ using System.Windows;
using ICSharpCode.Decompiler; using ICSharpCode.Decompiler;
using ICSharpCode.Decompiler.Metadata; using ICSharpCode.Decompiler.Metadata;
using ICSharpCode.Decompiler.TypeSystem; using ICSharpCode.Decompiler.TypeSystem;
using ICSharpCode.Decompiler.Util;
using ICSharpCode.ILSpyX; using ICSharpCode.ILSpyX;
using ICSharpCode.ILSpyX.TreeView; using ICSharpCode.ILSpyX.TreeView;
using ICSharpCode.ILSpyX.TreeView.PlatformAbstractions; using ICSharpCode.ILSpyX.TreeView.PlatformAbstractions;

2
ILSpy/TreeNodes/AssemblyTreeNode.cs

@ -712,7 +712,7 @@ namespace ICSharpCode.ILSpy.TreeNodes
node.RaisePropertyChanged(nameof(ILSpyTreeNode.IsAutoLoaded)); node.RaisePropertyChanged(nameof(ILSpyTreeNode.IsAutoLoaded));
} }
} }
MainWindow.Instance.AssemblyTreeModel.CurrentAssemblyList.RefreshSave(); MainWindow.Instance.AssemblyTreeModel.AssemblyList.RefreshSave();
} }
} }

2
ILSpy/TreeNodes/ILSpyTreeNode.cs

@ -85,7 +85,7 @@ namespace ICSharpCode.ILSpy.TreeNodes
return false; return false;
} }
protected internal override void OnChildrenChanged(NotifyCollectionChangedEventArgs e) public override void OnChildrenChanged(NotifyCollectionChangedEventArgs e)
{ {
if (e.NewItems != null) if (e.NewItems != null)
{ {

10
ILSpy/Util/MessageBus.cs

@ -22,16 +22,16 @@ namespace ICSharpCode.ILSpy.Util
public static class MessageBus<T> public static class MessageBus<T>
where T : EventArgs where T : EventArgs
{ {
private static readonly WeakEventSource<T> Subscriptions = new(); private static readonly WeakEventSource<T> subscriptions = new();
public static event EventHandler<T> Subscribers { public static event EventHandler<T> Subscribers {
add => Subscriptions.Subscribe(value); add => subscriptions.Subscribe(value);
remove => Subscriptions.Unsubscribe(value); remove => subscriptions.Unsubscribe(value);
} }
public static void Send(object sender, T e) public static void Send(object sender, T e)
{ {
Subscriptions.Raise(sender, e); subscriptions.Raise(sender, e);
} }
} }
@ -56,8 +56,6 @@ namespace ICSharpCode.ILSpy.Util
public class SessionSettingsChangedEventArgs(PropertyChangedEventArgs e) : WrappedEventArgs<PropertyChangedEventArgs>(e); public class SessionSettingsChangedEventArgs(PropertyChangedEventArgs e) : WrappedEventArgs<PropertyChangedEventArgs>(e);
public class DockWorkspaceActiveTabPageChangedEventArgs : EventArgs;
public class NavigateToReferenceEventArgs(object reference, bool inNewTabPage = false) : EventArgs public class NavigateToReferenceEventArgs(object reference, bool inNewTabPage = false) : EventArgs
{ {
public object Reference { get; } = reference; public object Reference { get; } = reference;

2
ILSpy/Views/OpenFromGacDialog.xaml.cs

@ -31,6 +31,8 @@ using ICSharpCode.Decompiler.Metadata;
using ICSharpCode.ILSpy.Controls; using ICSharpCode.ILSpy.Controls;
using ICSharpCode.ILSpyX.Extensions; using ICSharpCode.ILSpyX.Extensions;
using TomsToolbox.Essentials;
namespace ICSharpCode.ILSpy namespace ICSharpCode.ILSpy
{ {
/// <summary> /// <summary>

2
TestPlugin/MainMenuCommand.cs

@ -23,7 +23,7 @@ namespace TestPlugin
{ {
public override void Execute(object parameter) public override void Execute(object parameter)
{ {
foreach (var loadedAssembly in MainWindow.Instance.AssemblyTreeModel.CurrentAssemblyList.GetAssemblies()) foreach (var loadedAssembly in MainWindow.Instance.AssemblyTreeModel.AssemblyList.GetAssemblies())
{ {
loadedAssembly.AssemblyList.Unload(loadedAssembly); loadedAssembly.AssemblyList.Unload(loadedAssembly);
} }

Loading…
Cancel
Save