diff options
author | Lluis Sanchez <lluis@novell.com> | 2009-07-02 22:35:49 +0400 |
---|---|---|
committer | Lluis Sanchez <lluis@novell.com> | 2009-07-02 22:35:49 +0400 |
commit | 077e639ae200311eaac55377e95f8d28a9a86e27 (patch) | |
tree | 0c107bdce891d122f9cbdf720746a78166fffe9e /main/src/core/MonoDevelop.Ide/MonoDevelop.Ide.Execution | |
parent | b7722cbd33cf859695e78cac28cf077d903c0805 (diff) | |
parent | 6b4069af23b2a81e012d0d85d13fd63181d59fa1 (diff) |
* Makefile.am:
* gtk-gui/gui.stetic:
* MonoDevelop.Ide.csproj:
* MonoDevelop.Ide.addin.xml:
* MonoDevelop.Ide.Commands/ProjectCommands.cs:
* MonoDevelop.Ide.Execution/CustomExecutionMode.cs:
* MonoDevelop.Ide.Execution/IExecutionModeEditor.cs:
* MonoDevelop.Ide.Execution/CustomArgsCustomizer.cs:
* MonoDevelop.Ide.Execution/CommandExecutionContext.cs:
* MonoDevelop.Ide.Execution/CustomArgsExecutionMode.cs:
* MonoDevelop.Ide.Gui.Components/ExecutionModeComboBox.cs:
* MonoDevelop.Ide.Gui.Dialogs/CustomExecutionModeWidget.cs:
* MonoDevelop.Ide.Gui.Dialogs/CustomExecutionModeDialog.cs:
* MonoDevelop.Ide.Execution/ExecutionModeCommandService.cs:
* MonoDevelop.Ide.Execution/IExecutionCommandCustomizer.cs:
* gtk-gui/MonoDevelop.Ide.Gui.Dialogs.TipOfTheDayWindow.cs:
* MonoDevelop.Ide.Execution/IExecutionConfigurationEditor.cs:
* MonoDevelop.Ide.Execution/ParameterizedExecutionHandler.cs:
* gtk-gui/MonoDevelop.Ide.Gui.Components.ExecutionModeComboBox.cs:
* MonoDevelop.Ide.Gui.Dialogs/CustomExecutionModeManagerDialog.cs:
* gtk-gui/MonoDevelop.Ide.Gui.Dialogs.CustomExecutionModeWidget.cs:
* gtk-gui/MonoDevelop.Ide.Gui.Dialogs.CustomExecutionModeDialog.cs:
* gtk-gui/MonoDevelop.Ide.Gui.Dialogs.CustomExecutionModeManagerDialog.cs:
Finished support for custom execution modes.
* MonoDevelop.Ide.Gui/Document.cs:
* MonoDevelop.Ide.Gui/ProjectOperations.cs: Use the shared default
execution handler.
svn path=/trunk/monodevelop/; revision=137318
Diffstat (limited to 'main/src/core/MonoDevelop.Ide/MonoDevelop.Ide.Execution')
-rw-r--r-- | main/src/core/MonoDevelop.Ide/MonoDevelop.Ide.Execution/CommandExecutionContext.cs | 25 | ||||
-rw-r--r-- | main/src/core/MonoDevelop.Ide/MonoDevelop.Ide.Execution/CustomArgsCustomizer.cs (renamed from main/src/core/MonoDevelop.Ide/MonoDevelop.Ide.Execution/CustomArgsExecutionMode.cs) | 37 | ||||
-rw-r--r-- | main/src/core/MonoDevelop.Ide/MonoDevelop.Ide.Execution/CustomExecutionMode.cs | 162 | ||||
-rw-r--r-- | main/src/core/MonoDevelop.Ide/MonoDevelop.Ide.Execution/ExecutionModeCommandService.cs | 428 | ||||
-rw-r--r-- | main/src/core/MonoDevelop.Ide/MonoDevelop.Ide.Execution/IExecutionCommandCustomizer.cs | 39 | ||||
-rw-r--r-- | main/src/core/MonoDevelop.Ide/MonoDevelop.Ide.Execution/IExecutionConfigurationEditor.cs (renamed from main/src/core/MonoDevelop.Ide/MonoDevelop.Ide.Execution/IExecutionModeEditor.cs) | 5 | ||||
-rw-r--r-- | main/src/core/MonoDevelop.Ide/MonoDevelop.Ide.Execution/ParameterizedExecutionHandler.cs | 28 |
7 files changed, 550 insertions, 174 deletions
diff --git a/main/src/core/MonoDevelop.Ide/MonoDevelop.Ide.Execution/CommandExecutionContext.cs b/main/src/core/MonoDevelop.Ide/MonoDevelop.Ide.Execution/CommandExecutionContext.cs index 068436af32..e2217a5b33 100644 --- a/main/src/core/MonoDevelop.Ide/MonoDevelop.Ide.Execution/CommandExecutionContext.cs +++ b/main/src/core/MonoDevelop.Ide/MonoDevelop.Ide.Execution/CommandExecutionContext.cs @@ -61,5 +61,30 @@ namespace MonoDevelop.Ide.Execution else return false; } + + public ExecutionCommand GetTargetCommand () + { + if (cmd != null) + return cmd; + SpyHandler sh = new SpyHandler (); + runCheckDelegate (sh); + return cmd = sh.Command; + } + + class SpyHandler: IExecutionHandler + { + public ExecutionCommand Command; + + public bool CanExecute (ExecutionCommand command) + { + Command = command; + return true; + } + + public IProcessAsyncOperation Execute (MonoDevelop.Core.Execution.ExecutionCommand command, MonoDevelop.Core.Execution.IConsole console) + { + throw new InvalidOperationException (); + } + } } } diff --git a/main/src/core/MonoDevelop.Ide/MonoDevelop.Ide.Execution/CustomArgsExecutionMode.cs b/main/src/core/MonoDevelop.Ide/MonoDevelop.Ide.Execution/CustomArgsCustomizer.cs index 5588749899..6a251dbdd0 100644 --- a/main/src/core/MonoDevelop.Ide/MonoDevelop.Ide.Execution/CustomArgsExecutionMode.cs +++ b/main/src/core/MonoDevelop.Ide/MonoDevelop.Ide.Execution/CustomArgsCustomizer.cs @@ -34,22 +34,19 @@ using MonoDevelop.Projects; namespace MonoDevelop.Ide.Execution { [DataInclude (typeof(CustomArgsExecutionModeData))] - class CustomArgsExecutionHandler: ParameterizedExecutionHandler + class CustomArgsCustomizer: IExecutionCommandCustomizer { - public override bool CanExecute (ExecutionCommand command) + public IExecutionConfigurationEditor CreateEditor () { - if (!(command is ProcessExecutionCommand)) - return false; - foreach (IExecutionModeSet mset in Runtime.ProcessService.GetExecutionModes ()) { - foreach (IExecutionMode mode in mset.ExecutionModes) { - if (mode.ExecutionHandler.CanExecute (command)) - return true; - } - } - return Runtime.ProcessService.DefaultExecutionHandler.CanExecute (command); + return new MonoDevelop.Ide.Gui.Dialogs.CustomExecutionModeWidget (); } - - public override IProcessAsyncOperation Execute (ExecutionCommand command, IConsole console, CommandExecutionContext ctx, object configurationData) + + public bool CanCustomize (ExecutionCommand cmd) + { + return cmd is ProcessExecutionCommand; + } + + public void Customize (ExecutionCommand command, object configurationData) { CustomArgsExecutionModeData data = (CustomArgsExecutionModeData) configurationData; @@ -62,18 +59,6 @@ namespace MonoDevelop.Ide.Execution cmd.WorkingDirectory = data.WorkingDirectory; foreach (KeyValuePair<string,string> var in data.EnvironmentVariables) cmd.EnvironmentVariables [var.Key] = var.Value; - - if (string.IsNullOrEmpty (data.ModeId)) - return Runtime.ProcessService.DefaultExecutionHandler.Execute (command, console); - else { - IExecutionMode targetMode = ExecutionModeCommandService.GetExecutionMode (ctx, data.ModeId); - return targetMode.ExecutionHandler.Execute (command, console); - } - } - - public override IExecutionModeEditor CreateEditor () - { - return new MonoDevelop.Ide.Gui.Dialogs.CustomExecutionModeWidget (); } } @@ -83,8 +68,6 @@ namespace MonoDevelop.Ide.Execution public string Arguments { get; set; } [ItemProperty (DefaultValue="")] public string WorkingDirectory { get; set; } - [ItemProperty (DefaultValue="")] - public string ModeId; [ItemProperty] public Dictionary<string,string> EnvironmentVariables = new Dictionary<string, string> (); } diff --git a/main/src/core/MonoDevelop.Ide/MonoDevelop.Ide.Execution/CustomExecutionMode.cs b/main/src/core/MonoDevelop.Ide/MonoDevelop.Ide.Execution/CustomExecutionMode.cs new file mode 100644 index 0000000000..102590caf0 --- /dev/null +++ b/main/src/core/MonoDevelop.Ide/MonoDevelop.Ide.Execution/CustomExecutionMode.cs @@ -0,0 +1,162 @@ +// +// CustomExecutionMode.cs +// +// Author: +// Lluis Sanchez Gual <lluis@novell.com> +// +// Copyright (c) 2009 Novell, Inc (http://www.novell.com) +// +// 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; +using System.IO; +using System.Collections.Generic; +using MonoDevelop.Components.Commands; +using MonoDevelop.Core.Execution; +using MonoDevelop.Core; +using MonoDevelop.Ide.Gui.Dialogs; +using MonoDevelop.Projects; +using MonoDevelop.Core.Serialization; +using Mono.Addins; + +namespace MonoDevelop.Ide.Execution +{ + class CustomExecutionModes + { + [ItemProperty] + [ItemProperty ("Mode", Scope="*")] + [ExpandedCollection] + public List<CustomExecutionMode> Data = new List<CustomExecutionMode> (); + } + + class CustomExecutionMode: IExecutionMode, IExecutionHandler + { + [ItemProperty] + public string Name { get; set; } + + [ItemProperty] + public string Id { get; set; } + + [ItemProperty] + public string ModeId { get; set; } + + [ItemProperty (FallbackType=typeof(UnknownModeData))] + public object Data { get; set; } + + [ItemProperty ("CommandData")] + [ItemProperty (Scope="value", FallbackType=typeof(UnknownModeData))] + Dictionary<string,object> commandData; + + [ItemProperty (DefaultValue=false)] + public bool PromptForParameters { get; set; } + + public Project Project { get; set; } + + public CustomModeScope Scope { get; set; } + + IExecutionMode mode; + + public object GetCommandData (string editorId) + { + object data = null; + if (commandData != null) + commandData.TryGetValue (editorId, out data); + return data; + } + + public void SetCommandData (string editorId, object data) + { + if (commandData == null) + commandData = new Dictionary<string, object> (); + commandData [editorId] = data; + } + + public IExecutionHandler ExecutionHandler { + get { return this; } + } + + public IExecutionMode Mode { + get { + if (mode != null) + return mode; + foreach (IExecutionModeSet mset in Runtime.ProcessService.GetExecutionModes ()) { + foreach (IExecutionMode m in mset.ExecutionModes) { + if (m.Id == ModeId) + return mode = m; + } + } + return null; + } + set { + mode = value; + ModeId = value.Id; + } + } + + #region IExecutionHandler implementation + public bool CanExecute (ExecutionCommand command) + { + if (Mode != null) + return Mode.ExecutionHandler.CanExecute (command); + return false; + } + + public IProcessAsyncOperation Execute (ExecutionCommand command, IConsole console) + { + return Execute (command, console, true, false); + } + + public IProcessAsyncOperation Execute (ExecutionCommand command, IConsole console, bool allowPrompt, bool forcePrompt) + { + if ((PromptForParameters || forcePrompt) && allowPrompt) { + CommandExecutionContext ctx = new CommandExecutionContext (Project, command); + CustomExecutionMode customMode = ExecutionModeCommandService.ShowParamtersDialog (ctx, Mode, this); + if (customMode == null) + return new CancelledProcessAsyncOperation (); + else + return customMode.Execute (command, console, false, false); + } + if (commandData != null) { + foreach (KeyValuePair<string,object> cmdData in commandData) { + ExecutionCommandCustomizer cc = ExecutionModeCommandService.GetExecutionCommandCustomizer (cmdData.Key); + if (cc != null) + cc.Customize (command, cmdData.Value); + } + } + ParameterizedExecutionHandler cmode = Mode.ExecutionHandler as ParameterizedExecutionHandler; + if (cmode != null) { + CommandExecutionContext ctx = new CommandExecutionContext (Project, command); + return cmode.Execute (command, console, ctx, Data); + } else + return Mode.ExecutionHandler.Execute (command, console); + } + #endregion + } + + class UnknownModeData + { + } + + internal enum CustomModeScope + { + Project = 0, + Solution = 1, + Global = 2 + } +} diff --git a/main/src/core/MonoDevelop.Ide/MonoDevelop.Ide.Execution/ExecutionModeCommandService.cs b/main/src/core/MonoDevelop.Ide/MonoDevelop.Ide.Execution/ExecutionModeCommandService.cs index 53e1fc6038..68786f0e4d 100644 --- a/main/src/core/MonoDevelop.Ide/MonoDevelop.Ide.Execution/ExecutionModeCommandService.cs +++ b/main/src/core/MonoDevelop.Ide/MonoDevelop.Ide.Execution/ExecutionModeCommandService.cs @@ -25,75 +25,201 @@ // THE SOFTWARE. using System; +using System.IO; using System.Collections.Generic; using MonoDevelop.Components.Commands; using MonoDevelop.Core.Execution; using MonoDevelop.Core; +using MonoDevelop.Core.Gui; using MonoDevelop.Ide.Gui.Dialogs; using MonoDevelop.Projects; using MonoDevelop.Core.Serialization; +using Mono.Addins; namespace MonoDevelop.Ide.Execution { - public class ExecutionModeCommandService + public static class ExecutionModeCommandService { + static CustomExecutionModes globalModes; + + internal static IEnumerable<ExecutionCommandCustomizer> GetExecutionCommandCustomizers (CommandExecutionContext ctx) + { + ExecutionCommand cmd = ctx.GetTargetCommand (); + if (cmd == null) + yield break; + foreach (ExecutionCommandCustomizer customizer in AddinManager.GetExtensionNodes ("/MonoDevelop/Ide/ExecutionCommandEditors", typeof(ExecutionCommandCustomizer))) { + if (customizer.CanCustomize (cmd)) + yield return customizer; + } + } + + internal static ExecutionCommandCustomizer GetExecutionCommandCustomizer (string id) + { + foreach (ExecutionCommandCustomizer customizer in AddinManager.GetExtensionNodes ("/MonoDevelop/Ide/ExecutionCommandEditors", typeof(ExecutionCommandCustomizer))) { + if (customizer.Id == id) + return customizer; + } + return null; + } + public static void GenerateExecutionModeCommands (Project project, CanExecuteDelegate runCheckDelegate, CommandArrayInfo info) { CommandExecutionContext ctx = new CommandExecutionContext (project, runCheckDelegate); - List<CustomExecutionMode> customModes = new List<CustomExecutionMode> (); - if (project != null) { - CustomExecutionModes modes = project.UserProperties.GetValue<CustomExecutionModes> ("MonoDevelop.Ide.CustomExecutionModes", GetDataContext ()); - if (modes != null) { - foreach (CustomExecutionMode mode in modes.Data) { - mode.Project = project; - if (runCheckDelegate (mode.ExecutionHandler)) - customModes.Add (mode); + foreach (List<IExecutionMode> modes in GetExecutionModeCommands (ctx, false, true)) { + foreach (IExecutionMode mode in modes) { + CommandInfo ci = info.Add (mode.Name, new CommandItem (ctx, mode)); + if ((mode.ExecutionHandler is ParameterizedExecutionHandler) || ((mode is CustomExecutionMode) && ((CustomExecutionMode)mode).PromptForParameters)) { + // It will prompt parameters + ci.Text += "..."; + } else { + // The parameters window will be shown if ctrl is pressed + ci.Description = ci.Text + " - " + GettextCatalog.GetString ("Hold Control key to display the execution parameters dialog."); } } + info.AddSeparator (); + } + info.AddSeparator (); + info.Add (GettextCatalog.GetString ("Custom Mode Manager..."), new CommandItem (ctx, null)); + } + + public static IExecutionHandler GetExecutionModeForCommand (object data) + { + CommandItem item = (CommandItem) data; + if (item.Mode == null) { + CustomExecutionModeManagerDialog dlg = new CustomExecutionModeManagerDialog (item.Context); + try { + dlg.Run (); + } finally { + dlg.Destroy (); + } + return null; } + if (item.Mode.ExecutionHandler is ParameterizedExecutionHandler) { + ParameterizedExecutionHandler cmode = (ParameterizedExecutionHandler) item.Mode.ExecutionHandler; + ParameterizedExecutionHandlerWrapper pw = new ParameterizedExecutionHandlerWrapper (); + pw.Handler = cmode; + pw.Context = item.Context; + pw.ParentMode = item.Mode; + return pw; + } + + // If control key is pressed, show the parameters dialog + Gdk.ModifierType mtype; + if (Gtk.Global.GetCurrentEventState (out mtype) && (mtype & Gdk.ModifierType.ControlMask) != 0) { + RunWithPromptHandler cmode = new RunWithPromptHandler (); + cmode.Context = item.Context; + cmode.Mode = item.Mode; + return cmode; + } + + return item.Mode.ExecutionHandler; + } + + internal static List<List<IExecutionMode>> GetExecutionModeCommands (CommandExecutionContext ctx, bool includeDefault, bool includeDefaultCustomizer) + { + List<List<IExecutionMode>> itemGroups = new List<List<IExecutionMode>> (); + + List<CustomExecutionMode> customModes = new List<CustomExecutionMode> (GetCustomModes (ctx)); + foreach (IExecutionModeSet mset in Runtime.ProcessService.GetExecutionModes ()) { - HashSet<IExecutionMode> setModes = new HashSet<IExecutionMode> (mset.ExecutionModes); + List<IExecutionMode> items = new List<IExecutionMode> (); + HashSet<string> setModes = new HashSet<string> (); foreach (IExecutionMode mode in mset.ExecutionModes) { - if (runCheckDelegate (mode.ExecutionHandler)) - info.Add (mode.Name, new CommandItem (ctx, mode)); + setModes.Add (mode.Id); + if (ctx.CanExecute (mode.ExecutionHandler) && (mode.Id != "Default" || includeDefault)) + items.Add (mode); + if (mode.Id == "Default" && includeDefaultCustomizer) { + CustomExecutionMode cmode = new CustomExecutionMode (); + cmode.Mode = mode; + cmode.Project = ctx.Project; + cmode.PromptForParameters = true; + cmode.Name = GettextCatalog.GetString ("Custom Parameters..."); + items.Add (cmode); + } } List<CustomExecutionMode> toRemove = new List<CustomExecutionMode> (); foreach (CustomExecutionMode cmode in customModes) { - if (setModes.Contains ((IExecutionMode)cmode.Mode)) { - info.Add (cmode.Name, new CommandItem (ctx, cmode)); + if (setModes.Contains (cmode.Mode.Id)) { + if (ctx.CanExecute (cmode.Mode.ExecutionHandler)) + items.Add (cmode); toRemove.Add (cmode); } } foreach (CustomExecutionMode cmode in toRemove) customModes.Remove (cmode); - info.AddSeparator (); + if (items.Count > 0) + itemGroups.Add (items); } if (customModes.Count > 0) { - info.AddSeparator (); - foreach (CustomExecutionMode cmode in customModes) - info.Add (cmode.Name, new CommandItem (ctx, cmode)); + List<IExecutionMode> items = new List<IExecutionMode> (); + foreach (CustomExecutionMode cmode in customModes) { + if (ctx.CanExecute (cmode.ExecutionHandler)) + items.Add (cmode); + } + if (items.Count > 0) + itemGroups.Add (items); } + return itemGroups; } - public static IExecutionHandler GetExecutionModeForCommand (object data) + internal static IEnumerable<CustomExecutionMode> GetCustomModes (CommandExecutionContext ctx) { - CommandItem item = (CommandItem) data; - if (item.Mode.ExecutionHandler is ParameterizedExecutionHandler) { - ParameterizedExecutionHandler cmode = (ParameterizedExecutionHandler) item.Mode.ExecutionHandler; - ParameterizedExecutionHandlerWrapper pw = new ParameterizedExecutionHandlerWrapper (); - pw.Handler = cmode; - pw.Context = item.Context; - pw.ParentMode = item.Mode; - return pw; + if (ctx.Project != null) { + CustomExecutionModes modes = ctx.Project.UserProperties.GetValue<CustomExecutionModes> ("MonoDevelop.Ide.CustomExecutionModes", GetDataContext ()); + if (modes != null) { + foreach (CustomExecutionMode mode in modes.Data) { + mode.Project = ctx.Project; + if (ctx.CanExecute (mode.ExecutionHandler)) { + mode.Scope = CustomModeScope.Project; + yield return mode; + } + } + } + modes = ctx.Project.ParentSolution.UserProperties.GetValue<CustomExecutionModes> ("MonoDevelop.Ide.CustomExecutionModes", GetDataContext ()); + if (modes != null) { + foreach (CustomExecutionMode mode in modes.Data) { + mode.Project = ctx.Project; + if (ctx.CanExecute (mode.ExecutionHandler)) { + mode.Scope = CustomModeScope.Solution; + yield return mode; + } + } + } + } + foreach (CustomExecutionMode mode in GetGlobalCustomExecutionModes ().Data) { + if (ctx.CanExecute (mode.ExecutionHandler)) { + mode.Scope = CustomModeScope.Global; + yield return mode; + } } - return item.Mode.ExecutionHandler; } - class CommandItem + internal static CustomExecutionMode ShowParamtersDialog (CommandExecutionContext ctx, IExecutionMode mode, CustomExecutionMode currentMode) + { + CustomExecutionMode cmode = null; + + DispatchService.GuiSyncDispatch (delegate { + CustomExecutionModeDialog dlg = new CustomExecutionModeDialog (); + try { + dlg.Initialize (ctx, mode, currentMode); + if (dlg.Run () == (int) Gtk.ResponseType.Ok) { + cmode = dlg.GetConfigurationData (); + cmode.Project = ctx.Project; + if (dlg.Save) + SaveCustomCommand (ctx.Project, cmode); + } + } finally { + dlg.Destroy (); + } + }); + return cmode; + } + + internal class CommandItem { public IExecutionMode Mode; public CommandExecutionContext Context; @@ -116,39 +242,92 @@ namespace MonoDevelop.Ide.Execution } } - class ParameterizedExecutionHandlerWrapper: IExecutionHandler + internal static void SaveCustomCommand (Project project, CustomExecutionMode cmode) { - public ParameterizedExecutionHandler Handler; - public CommandExecutionContext Context; - public IExecutionMode ParentMode; - - public bool CanExecute (ExecutionCommand command) - { - return Handler.CanExecute (command); + CustomExecutionModes modes = GetCustomExecutionModeList (project, cmode.Scope); + bool found = false; + if (!string.IsNullOrEmpty (cmode.Id)) { + for (int n=0; n<modes.Data.Count; n++) { + if (modes.Data[n].Id == cmode.Id) { + modes.Data[n] = cmode; + found = true; + break; + } + } } - - public IProcessAsyncOperation Execute (ExecutionCommand command, IConsole console) - { - return Handler.InternalExecute (Context, ParentMode, command, console); + if (!found) { + cmode.Id = Guid.NewGuid ().ToString (); + modes.Data.Add (cmode); } + + if (cmode.Scope == CustomModeScope.Global) + SaveGlobalCustomExecutionModes (); + else + Ide.Gui.IdeApp.Workspace.SavePreferences (); } - internal static void SaveCustomCommand (Project project, IExecutionMode mode, string name, object data) + static CustomExecutionModes GetCustomExecutionModeList (Project project, CustomModeScope scope) { CustomExecutionModes modes; - if (project.UserProperties.HasValue ("MonoDevelop.Ide.CustomExecutionModes")) - modes = project.UserProperties.GetValue<CustomExecutionModes> ("MonoDevelop.Ide.CustomExecutionModes", GetDataContext ()); + if (scope == CustomModeScope.Global) { + modes = GetGlobalCustomExecutionModes (); + } else { - modes = new CustomExecutionModes (); - project.UserProperties.SetValue<CustomExecutionModes> ("MonoDevelop.Ide.CustomExecutionModes", modes); + PropertyBag props; + if (scope == CustomModeScope.Project) + props = project.UserProperties; + else + props = project.ParentSolution.UserProperties; + + if (props.HasValue ("MonoDevelop.Ide.CustomExecutionModes")) + modes = props.GetValue<CustomExecutionModes> ("MonoDevelop.Ide.CustomExecutionModes", GetDataContext ()); + else { + modes = new CustomExecutionModes (); + props.SetValue<CustomExecutionModes> ("MonoDevelop.Ide.CustomExecutionModes", modes); + } + } + return modes; + } + + internal static void RemoveCustomCommand (Project project, CustomExecutionMode cmode) + { + CustomExecutionModes modes = GetCustomExecutionModeList (project, cmode.Scope); + modes.Data.Remove (cmode); + if (cmode.Scope == CustomModeScope.Global) + SaveGlobalCustomExecutionModes (); + else + Ide.Gui.IdeApp.Workspace.SavePreferences (); + } + + static CustomExecutionModes GetGlobalCustomExecutionModes () + { + if (globalModes == null) { + try { + XmlDataSerializer ser = new XmlDataSerializer (GetDataContext ()); + FilePath file = PropertyService.ConfigPath.Combine ("custom-command-modes.xml"); + if (File.Exists (file)) + globalModes = (CustomExecutionModes) ser.Deserialize (file, typeof(CustomExecutionModes)); + } catch (Exception ex) { + LoggingService.LogError ("Could not load global custom execution modes.", ex); + } + + if (globalModes == null) + globalModes = new CustomExecutionModes (); + } + return globalModes; + } + + static void SaveGlobalCustomExecutionModes () + { + if (globalModes == null) + return; + try { + XmlDataSerializer ser = new XmlDataSerializer (GetDataContext ()); + FilePath file = PropertyService.ConfigPath.Combine ("custom-command-modes.xml"); + ser.Serialize (file, globalModes, typeof(CustomExecutionModes)); + } catch (Exception ex) { + LoggingService.LogError ("Could not save global custom execution modes.", ex); } - CustomExecutionMode cmode = new CustomExecutionMode (); - cmode.Mode = mode; - cmode.Data = data; - cmode.Name = name; - cmode.Id = "__PRJ_" + mode.Id + "_" + (++modes.LastId); - modes.Data.Add (cmode); - Ide.Gui.IdeApp.Workspace.SavePreferences (); } static DataContext dataContext = new DataContext (); @@ -161,6 +340,9 @@ namespace MonoDevelop.Ide.Execution dataContext.IncludeType (mode.ExecutionHandler.GetType ()); } } + foreach (ExecutionCommandCustomizer customizer in AddinManager.GetExtensionNodes ("/MonoDevelop/Ide/ExecutionCommandEditors", typeof(ExecutionCommandCustomizer))) { + dataContext.IncludeType (customizer.Type); + } return dataContext; } @@ -182,83 +364,87 @@ namespace MonoDevelop.Ide.Execution yield return mode; } } - if (ctx.Project != null) { - CustomExecutionModes modes = ctx.Project.UserProperties.GetValue<CustomExecutionModes> ("MonoDevelop.Ide.CustomExecutionModes", GetDataContext ()); - if (modes != null) { - foreach (CustomExecutionMode mode in modes.Data) { - if (ctx.CanExecute (mode)) - yield return mode; - } - } + + foreach (CustomExecutionMode mode in GetCustomModes (ctx)) { + if (ctx.CanExecute (mode)) + yield return mode; } } + } + + class ExecutionCommandCustomizer: TypeExtensionNode, IExecutionCommandCustomizer + { + IExecutionCommandCustomizer customizer; - class CustomExecutionModes + [NodeAttribute ("_name")] + string name; + + protected override void Read (Mono.Addins.NodeElement elem) { - [ItemProperty] - public int LastId; - - [ItemProperty] - [ItemProperty ("Mode", Scope="*")] - [ExpandedCollection] - public List<CustomExecutionMode> Data = new List<CustomExecutionMode> (); + base.Read (elem); + customizer = (IExecutionCommandCustomizer) GetInstance (typeof(IExecutionCommandCustomizer)); } - class CustomExecutionMode: IExecutionMode, IExecutionHandler + public bool CanCustomize (ExecutionCommand cmd) { - [ItemProperty] - public string Name { get; set; } - - [ItemProperty] - public string Id { get; set; } - - [ItemProperty] - public string ModeId; - - [ItemProperty] - public object Data; - - public Project Project; - - IExecutionMode mode; - - public IExecutionHandler ExecutionHandler { - get { return this; } - } - - public IExecutionMode Mode { - get { - if (mode != null) - return mode; - foreach (IExecutionModeSet mset in Runtime.ProcessService.GetExecutionModes ()) { - foreach (IExecutionMode m in mset.ExecutionModes) { - if (m.Id == ModeId) - return mode = m; - } - } - return null; - } - set { - mode = value; - ModeId = value.Id; - } - } - - #region IExecutionHandler implementation - public bool CanExecute (ExecutionCommand command) - { - if (Mode != null) - return Mode.ExecutionHandler.CanExecute (command); - return false; + return customizer.CanCustomize (cmd); + } + + public void Customize (ExecutionCommand cmd, object data) + { + customizer.Customize (cmd, data); + } + + public IExecutionConfigurationEditor CreateEditor () + { + return customizer.CreateEditor (); + } + + public string Name { + get { + return name; } - - public IProcessAsyncOperation Execute (ExecutionCommand command, IConsole console) - { - ParameterizedExecutionHandler cmode = Mode.ExecutionHandler as ParameterizedExecutionHandler; - CommandExecutionContext ctx = new CommandExecutionContext (Project, command); - return cmode.Execute (command, console, ctx, Data); + } + } + + class RunWithPromptHandler: IExecutionHandler + { + public IExecutionMode Mode; + public CommandExecutionContext Context; + + public bool CanExecute (ExecutionCommand command) + { + return Mode.ExecutionHandler.CanExecute (command); + } + + public IProcessAsyncOperation Execute (ExecutionCommand command, IConsole console) + { + if (Mode is CustomExecutionMode) + return ((CustomExecutionMode)Mode).Execute (command, console, true, true); + else { + CustomExecutionMode cmode = new CustomExecutionMode (); + cmode.Mode = Mode; + cmode.Project = Context.Project; + cmode.PromptForParameters = true; + return cmode.ExecutionHandler.Execute (command, console); } - #endregion + } + } + + class ParameterizedExecutionHandlerWrapper: IExecutionHandler + { + public ParameterizedExecutionHandler Handler; + public CommandExecutionContext Context; + public IExecutionMode ParentMode; + + public bool CanExecute (ExecutionCommand command) + { + return Handler.CanExecute (command); + } + + public IProcessAsyncOperation Execute (ExecutionCommand command, IConsole console) + { + return Handler.InternalExecute (Context, ParentMode, command, console); } } } diff --git a/main/src/core/MonoDevelop.Ide/MonoDevelop.Ide.Execution/IExecutionCommandCustomizer.cs b/main/src/core/MonoDevelop.Ide/MonoDevelop.Ide.Execution/IExecutionCommandCustomizer.cs new file mode 100644 index 0000000000..a0ed101019 --- /dev/null +++ b/main/src/core/MonoDevelop.Ide/MonoDevelop.Ide.Execution/IExecutionCommandCustomizer.cs @@ -0,0 +1,39 @@ +// +// IExecutionCommandEditor.cs +// +// Author: +// Lluis Sanchez Gual <lluis@novell.com> +// +// Copyright (c) 2009 Novell, Inc (http://www.novell.com) +// +// 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; +using MonoDevelop.Core.Execution; + + +namespace MonoDevelop.Ide.Execution +{ + public interface IExecutionCommandCustomizer + { + bool CanCustomize (ExecutionCommand cmd); + void Customize (ExecutionCommand cmd, object data); + IExecutionConfigurationEditor CreateEditor (); + } +} diff --git a/main/src/core/MonoDevelop.Ide/MonoDevelop.Ide.Execution/IExecutionModeEditor.cs b/main/src/core/MonoDevelop.Ide/MonoDevelop.Ide.Execution/IExecutionConfigurationEditor.cs index 6f2520905f..ce6223c0b9 100644 --- a/main/src/core/MonoDevelop.Ide/MonoDevelop.Ide.Execution/IExecutionModeEditor.cs +++ b/main/src/core/MonoDevelop.Ide/MonoDevelop.Ide.Execution/IExecutionConfigurationEditor.cs @@ -28,10 +28,9 @@ using System; namespace MonoDevelop.Ide.Execution { - public interface IExecutionModeEditor + public interface IExecutionConfigurationEditor { - Gtk.Widget Control { get; } - void Load (CommandExecutionContext ctx, object data); + Gtk.Widget Load (CommandExecutionContext ctx, object data); object Save (); } } diff --git a/main/src/core/MonoDevelop.Ide/MonoDevelop.Ide.Execution/ParameterizedExecutionHandler.cs b/main/src/core/MonoDevelop.Ide/MonoDevelop.Ide.Execution/ParameterizedExecutionHandler.cs index bd203054d2..2cb18f0ab5 100644 --- a/main/src/core/MonoDevelop.Ide/MonoDevelop.Ide.Execution/ParameterizedExecutionHandler.cs +++ b/main/src/core/MonoDevelop.Ide/MonoDevelop.Ide.Execution/ParameterizedExecutionHandler.cs @@ -45,34 +45,16 @@ namespace MonoDevelop.Ide.Execution internal IProcessAsyncOperation InternalExecute (CommandExecutionContext ctx, IExecutionMode mode, ExecutionCommand command, IConsole console) { - object synch = new object (); + CustomExecutionMode cmode = ExecutionModeCommandService.ShowParamtersDialog (ctx, mode, null); + if (cmode == null) + return new CancelledProcessAsyncOperation (); - var done = new System.Threading.ManualResetEvent (false); - IProcessAsyncOperation result = new CancelledProcessAsyncOperation (); - - Gtk.Application.Invoke (delegate { - CustomExecutionModeDialog dlg = new CustomExecutionModeDialog (); - try { - dlg.Initialize (ctx, this, null); - if (dlg.Run () == (int) Gtk.ResponseType.Ok) { - object mdata = dlg.GetConfigurationData (); - if (dlg.Save && ctx.Project != null) - ExecutionModeCommandService.SaveCustomCommand (ctx.Project, mode, dlg.ModeName, mdata); - result = Execute (command, console, ctx, mdata); - } - } finally { - dlg.Destroy (); - done.Set (); - } - }); - - done.WaitOne (); - return result; + return cmode.Execute (command, console, false, false); } public abstract IProcessAsyncOperation Execute (ExecutionCommand command, IConsole console, CommandExecutionContext ctx, object configurationData); - public abstract IExecutionModeEditor CreateEditor (); + public abstract IExecutionConfigurationEditor CreateEditor (); } |