📄 extendercontrolbasedesigner.pagemethodsignatures.cs
字号:
UndoContext undo = automation.UndoContext;
if (undo != null && undo.Reference != null && undo.IsOpen)
{
undo = null;
}
try
{
CodeFunction2 method = FindMethod(classModel, name, _signature);
if (method != null && method.Reference != null)
{
if (PageMethodNeedsRepair(method) && (ShowMessage(string.Format(CultureInfo.CurrentCulture, "Would you like to repair the existing page method \"{0}\"?", name), MessageBoxButtons.YesNo) == DialogResult.Yes))
{
// Repair an existing page method
if (undo != null)
{
undo.Open(string.Format(CultureInfo.CurrentCulture, "Repair \"{0}\" page method", name), false);
}
RepairPageMethod(method);
}
}
else
{
// Create a new page method
if (undo != null)
{
undo.Open(string.Format(CultureInfo.CurrentCulture, "Add \"{0}\" page method", name), false);
}
CreatePageMethod(classModel, name);
}
}
finally
{
if (undo != null && undo.IsOpen)
{
undo.Close();
}
}
}
finally
{
UnloadWebProjectItem(automation.ActiveDocument.ProjectItem);
}
}
catch (Exception ex)
{
ShowMessage(string.Format(CultureInfo.CurrentCulture, "Unexpected error ({0}): {1}{2}{3}", ex.GetType().Name, ex.Message, Environment.NewLine, ex.StackTrace));
}
}
/// <summary>
/// Get a valid reference to a required service
/// </summary>
/// <typeparam name="S">Type of the service</typeparam>
/// <param name="service">Value of the service to be assigned</param>
/// <returns>True if the service was found, false otherwise</returns>
[System.Diagnostics.CodeAnalysis.SuppressMessage("Microsoft.Security", "CA2116:AptcaMethodsShouldOnlyCallAptcaMethods", Justification = "Security handled by base class")]
private bool EnsureService<S>(out S service) where S : class
{
service = GetService(typeof(S)) as S;
if (service == null)
{
ShowMessage(string.Format(CultureInfo.CurrentCulture, "Cannot create page method \"{0}\" because {1} could not be acquired!", _signature.DeclaringType.Name, typeof(S).Name));
return false;
}
return true;
}
/// <summary>
/// Show a message
/// </summary>
/// <param name="message">Message</param>
/// <param name="buttons">Buttons</param>
/// <returns>Result</returns>
private static DialogResult ShowMessage(string message)
{
return ShowMessage(message, MessageBoxButtons.OK);
}
/// <summary>
/// Show a message
/// </summary>
/// <param name="message">Message</param>
/// <param name="buttons">Buttons</param>
/// <returns>Result</returns>
[System.Diagnostics.CodeAnalysis.SuppressMessage("Microsoft.Globalization", "CA1300:SpecifyMessageBoxOptions", Justification = "Messages are not localized")]
private static DialogResult ShowMessage(string message, MessageBoxButtons buttons)
{
return MessageBox.Show(message, "Ajax Control Toolkit", buttons);
}
/// <summary>
/// Find the CodeModel node for a given class
/// </summary>
/// <param name="model">FileCodeModel containing the class</param>
/// <param name="name">Name of the class</param>
/// <returns>CodeModel node for the class, or null if not found</returns>
[System.Diagnostics.CodeAnalysis.SuppressMessage("Microsoft.Security", "CA2116:AptcaMethodsShouldOnlyCallAptcaMethods", Justification = "Security handled by base class")]
private static CodeClass2 FindClass(FileCodeModel2 model, string name)
{
// Create a queue to "recurse" through all the child elements of the file
Queue<CodeElement2> remaining = new Queue<CodeElement2>();
// Start with the top level elements
foreach (object element in model.CodeElements)
{
remaining.Enqueue(new CodeElement2(element));
}
// "Recurse" through their children
while (remaining.Count > 0)
{
CodeElement2 element = remaining.Dequeue();
// Ignore anything that isn't a type or a namespace
if (element == null || element.Reference == null || (!element.IsCodeType && element.Kind != vsCMElement.vsCMElementNamespace))
{
continue;
}
// If it's a class with a matching name, return it
if ((element.Kind == vsCMElement.vsCMElementClass) && (string.CompareOrdinal(element.FullName, name) == 0))
{
return new CodeClass2(element.Reference);
}
// Add any children of the type
if (element.Children != null)
{
foreach (object child in element.Children)
{
remaining.Enqueue(new CodeElement2(child));
}
}
}
// Return null if we couldn't find a node corresponding to the class name
return null;
}
/// <summary>
/// Find all CodeFunctions that correspond to overloads of a method with a given name
/// </summary>
/// <param name="classModel">Class to search for the methods</param>
/// <param name="name">Name of the methods</param>
/// <returns>Array of CodeFunctions representing the method overloads defined in the class</returns>
[System.Diagnostics.CodeAnalysis.SuppressMessage("Microsoft.Security", "CA2116:AptcaMethodsShouldOnlyCallAptcaMethods", Justification = "Security handled by base class")]
private static CodeFunction2[] FindMethods(CodeClass2 classModel, string name)
{
List<CodeFunction2> methods = new List<CodeFunction2>();
foreach (object child in classModel.Children)
{
CodeElement2 element = new CodeElement2(child);
if ((element.Reference == null) || (element.Kind != vsCMElement.vsCMElementFunction))
{
continue;
}
if (string.CompareOrdinal(element.Name, name) == 0)
{
methods.Add(new CodeFunction2(child));
}
}
return methods.ToArray();
}
/// <summary>
/// Find a CodeFunction that corresponds to a specific overload of a method
/// </summary>
/// <param name="classModel">Class to search for the method</param>
/// <param name="name">Name of the method</param>
/// <param name="signature">Signature of the method</param>
/// <returns>The CodeFunction representing the method if found, null if not found</returns>
[System.Diagnostics.CodeAnalysis.SuppressMessage("Microsoft.Security", "CA2116:AptcaMethodsShouldOnlyCallAptcaMethods", Justification = "Security handled by base class")]
private static CodeFunction2 FindMethod(CodeClass2 classModel, string name, MethodInfo signature)
{
ParameterInfo[] parameters = signature.GetParameters();
// Check each of the overloads to see if we have a matching signature
foreach (CodeFunction2 method in FindMethods(classModel, name))
{
if (method == null || method.Reference == null)
{
continue;
}
// Check the return type
if (!AreSameType(method.Type, signature.ReturnType))
{
continue;
}
// Check the number of parameters
if (method.Parameters.Count != parameters.Length)
{
continue;
}
// Check the types of each parameter
bool failed = false;
int i = 0;
foreach (object p in method.Parameters)
{
CodeParameter2 parameter = new CodeParameter2(p);
if ((parameter.Reference == null) || !AreSameType(parameter.Type, parameters[i++].ParameterType))
{
failed = true;
break;
}
}
if (!failed)
{
return method;
}
}
// Return null if no matching signature was found
return null;
}
/// <summary>
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -