// The Nova Project by Ken Beckett.
// Copyright (C) 2007-2012 Inevitable Software, all rights reserved.
// Released under the Common Development and Distribution License, CDDL-1.0: http://opensource.org/licenses/cddl1.php
using System;
using System.Collections.Generic;
using System.Reflection;
using System.Windows.Controls;
using System.Windows.Media;
using Mono.Cecil;
using Nova.CodeDOM;
namespace Nova.UI
{
/// <summary>
/// The view model for a <see cref="CodeDOM.SymbolicRef"/>.
/// </summary>
public abstract class SymbolicRefVM : ExpressionVM
{
#region /* CONSTRUCTORS */
/// <summary>
/// Create a view model instance for the specified <see cref="CodeDOM.SymbolicRef"/>.
/// </summary>
protected SymbolicRefVM(SymbolicRef symbolicRef, Dictionary<CodeObject, CodeObjectVM> dictionary)
: base(symbolicRef, dictionary)
{ }
#endregion
#region /* PROPERTIES */
/// <summary>
/// The underlying <see cref="CodeDOM.SymbolicRef"/> model.
/// </summary>
public SymbolicRef SymbolicRef
{
get { return (SymbolicRef)CodeObject; }
}
#endregion
#region /* METHODS */
#endregion
#region /* RENDERING */
protected internal override bool HasBorder()
{
return false;
}
protected virtual Brush RenderBrush(RenderFlags flags)
{
return IDENTIFIER_BRUSH;
}
public override void RenderExpression(CodeRenderer renderer, RenderFlags flags)
{
renderer.RenderText(SymbolicRef.Name, RenderBrush(flags), this);
}
public override void RenderToolTip(CodeRenderer renderer, RenderFlags flags)
{
TypeRefBaseVM.RenderType(renderer, CodeObject.GetType(), flags, this);
renderer.RenderRightArrow(NORMAL_BRUSH, this);
RenderReferenceDescription(renderer, SymbolicRef.Reference);
RenderSummaryCommentInToolTip(renderer);
RenderMessagesInToolTip(renderer, flags);
RenderImplicitConversions(renderer, flags); // Render any implicit conversion if being passed as an argument
}
protected virtual void RenderReferenceDescription(CodeRenderer renderer, object obj)
{
RenderDescription(renderer, obj, this);
}
public static void RenderDescription(CodeRenderer renderer, object obj, CodeObjectVM tag)
{
if (obj is CodeObject)
{
// Create a VM (used when displaying Possible Matches for an UnresolvedRef)
CodeObject codeObject = (CodeObject)obj;
CodeObjectVM codeObjectVM = CreateVM(codeObject, null, true);
codeObjectVM.RenderDescription(renderer);
if (tag == null)
tag = codeObjectVM;
// Hacky - set the Border tag to anything passed in (to display Messages for Possible Matches)
Border border = codeObjectVM.GetSelectionElement() as Border;
if (border != null)
border.Tag = tag;
// Indicate if the reference is to an object in another project
Project project = codeObject.FindParent<Project>();
if (project != null && project != tag.CodeObject.FindParent<Project>())
renderer.RenderText(" (in " + project.Name + ")", NORMAL_BRUSH, TextStyle.Proportional);
}
else if (obj is MemberReference)
{
MemberReference memberReference = (MemberReference)obj;
RenderDescription(renderer, memberReference, tag);
RenderReferencedAssembly(renderer, "in", memberReference.Module.Assembly);
}
else if (obj is ParameterDefinition)
{
ParameterDefinition parameterDefinition = (ParameterDefinition)obj;
ParameterRefVM.RenderParameterDefinition(renderer, parameterDefinition, RenderFlags.ForceBorder | RenderFlags.ShowParentTypes, tag);
IMethodSignature methodSignature = parameterDefinition.Method;
if (methodSignature is MethodDefinition)
RenderReferencedAssembly(renderer, "in", ((MethodDefinition)methodSignature).Module.Assembly);
}
else if (obj is MemberInfo)
{
MemberInfo memberInfo = (MemberInfo)obj;
RenderDescription(renderer, memberInfo, tag);
RenderReferencedAssembly(renderer, "in", memberInfo.Module.Assembly);
}
else if (obj is ParameterInfo)
{
ParameterInfo parameterInfo = (ParameterInfo)obj;
ParameterRefVM.RenderParameterInfo(renderer, parameterInfo, RenderFlags.ForceBorder | RenderFlags.ShowParentTypes, tag);
RenderReferencedAssembly(renderer, "in", parameterInfo.Member.Module.Assembly);
}
}
protected static void RenderDescription(CodeRenderer renderer, MemberReference memberReference, CodeObjectVM parentVM)
{
const RenderFlags flags = RenderFlags.ForceBorder | RenderFlags.ShowParentTypes;
if (memberReference is TypeReference) // TypeDefinition or GenericParameter
TypeRefBaseVM.RenderTypeReference(renderer, (TypeReference)memberReference, flags | RenderFlags.Description, parentVM);
else if (memberReference is MethodDefinition)
MethodRefVM.RenderMethodDefinition(renderer, (MethodDefinition)memberReference, flags, parentVM);
else if (memberReference is PropertyDefinition)
PropertyRefVM.RenderPropertyDefinition(renderer, (PropertyDefinition)memberReference, flags, parentVM);
else if (memberReference is FieldDefinition)
FieldRefVM.RenderFieldDefinition(renderer, (FieldDefinition)memberReference, flags, parentVM);
else if (memberReference is EventDefinition)
EventRefVM.RenderEventDefinition(renderer, (EventDefinition)memberReference, flags, parentVM);
else
renderer.RenderText(memberReference.ToString(), IDENTIFIER_BRUSH, parentVM);
}
protected static void RenderDescription(CodeRenderer renderer, MemberInfo memberInfo, CodeObjectVM parentVM)
{
const RenderFlags flags = RenderFlags.ForceBorder | RenderFlags.ShowParentTypes;
switch (memberInfo.MemberType)
{
case MemberTypes.TypeInfo:
case MemberTypes.NestedType:
TypeRefBaseVM.RenderType(renderer, (Type)memberInfo, flags | RenderFlags.Description, parentVM);
break;
case MemberTypes.Constructor:
ConstructorRefVM.RenderConstructorInfo(renderer, (ConstructorInfo)memberInfo, flags, parentVM);
break;
case MemberTypes.Method:
MethodRefVM.RenderMethodInfo(renderer, (MethodInfo)memberInfo, flags, parentVM);
break;
case MemberTypes.Property:
PropertyRefVM.RenderPropertyInfo(renderer, (PropertyInfo)memberInfo, flags, parentVM);
break;
case MemberTypes.Field:
FieldRefVM.RenderFieldInfo(renderer, (FieldInfo)memberInfo, flags, parentVM);
break;
case MemberTypes.Event:
EventRefVM.RenderEventInfo(renderer, (EventInfo)memberInfo, flags, parentVM);
break;
default:
renderer.RenderText(memberInfo.ToString(), IDENTIFIER_BRUSH, parentVM);
break;
}
}
protected static void RenderReferencedAssembly(CodeRenderer renderer, string prefix, AssemblyDefinition assembly)
{
AssemblyNameDefinition assemblyName = assembly.Name;
renderer.RenderText(" (" + prefix + " " + assemblyName.Name + " " + assemblyName.Version.Major + "." + assemblyName.Version.Minor + ")", NORMAL_BRUSH, TextStyle.Proportional);
}
protected static void RenderReferencedAssembly(CodeRenderer renderer, string prefix, Assembly assembly)
{
AssemblyName assemblyName = assembly.GetName();
renderer.RenderText(" (" + prefix + " " + assemblyName.Name + " " + assemblyName.Version.Major + "." + assemblyName.Version.Minor + ")", NORMAL_BRUSH, TextStyle.Proportional);
}
#endregion
}
}