using System.Collections.Generic;
using System.ComponentModel;
using System.Diagnostics.CodeAnalysis;
using System.Linq;
namespace Vanara.Windows.Shell;
/// A dictionary of Command Verbs defined in the Windows Registry.
///
public class CommandVerbDictionary : RegBasedDictionary
{
private const string rootKeyName = "shell";
private readonly RegBasedSettings parent;
internal CommandVerbDictionary(RegBasedSettings parent, bool readOnly) : base(parent.key?.OpenSubKey(rootKeyName, !readOnly), readOnly) => this.parent = parent;
/// Gets or sets the default verb.
/// The default verb.
[DefaultValue(null)]
public string? DefaultVerb
{
get => key?.GetValue(null)?.ToString();
set { if (ContainsKey(value)) key?.SetValue(null, value!); else throw new KeyNotFoundException("The command verb specified is not defined."); }
}
/// Get the filtered list of keys under the base.
[Browsable(false)]
public override IEnumerable Keys => key?.GetSubKeyNames() ?? new string[0];
/// Gets or sets the order of the command verbs.
/// The ordered list of command verbs.
[Browsable(false)]
public IList Order
{
get
{
var order = key?.GetValue("", null)?.ToString();
var vals = Values.ToList();
if (order != null)
{
var orderedItems = order.Split(new[] { ',' }, StringSplitOptions.RemoveEmptyEntries);
for (var i = orderedItems.Length - 1; i >= 0; i--)
{
var match = vals.Find(c =>
string.Equals(c.Name, orderedItems[i], StringComparison.InvariantCultureIgnoreCase));
if (match == null) continue;
vals.Remove(match);
vals.Insert(0, match);
}
}
return vals;
}
set
{
switch (value?.Count ?? 0)
{
case 0:
key?.DeleteValue("", false);
break;
case 1:
key?.SetValue("", value!.First().Name);
break;
default:
key?.SetValue("", string.Join(",", value!.Select(c => c.Name).ToArray()));
break;
}
}
}
/// Adds the specified command verb.
/// The command verb name.
///
/// The command verb display name. This is the string shown to the user when requesting a context menu for a shell item.
///
/// The command to execute.
/// if set to set this verb as default.
/// A instance which has been added to the registry.
public CommandVerb Add(string verb, string? displayName = null, string? command = null, bool setAsDefault = false)
{
if (key == null && !readOnly)
key = parent.key?.CreateSubKey(rootKeyName);
var vkey = key?.CreateSubKey(verb) ?? throw new InvalidOperationException("Unable to create required key in registry.");
var v = new CommandVerb(vkey, verb, false) { DisplayName = displayName, Command = command };
if (setAsDefault) key?.SetValue(null, verb);
return v;
}
/// Determines if a specified key is in the filtered list of keys under the base.
/// The name of the key to check.
/// if the key is found; otherwise .
public override bool ContainsKey(string? verb) => verb is null ? false : key?.HasSubKey(verb) ?? false;
/// Removes the specified key from this dictionary and the registry.
/// The name of the command verb to remove.
/// A value indicating success () or failure ().
public bool Remove(string verb)
{
try
{
key?.DeleteSubKeyTree(verb);
return true;
}
catch
{
return false;
}
}
/// Tries to get the with the name .
/// The verb name.
/// On success, the corresponding instance; on failure.
/// A value indicating if was found.
public override bool TryGetValue(string verb, [NotNullWhen(true)] out CommandVerb? value)
{
value = null;
if (!ContainsKey(verb)) return false;
value = new CommandVerb(key?.OpenSubKey(verb, !readOnly)!, verb, readOnly);
return true;
}
}