/// <summary> /// Creates the new item expression that creates the object and initial mapping. /// </summary> /// <param name="controlType">Type of the control.</param> /// <returns>The initial creation lambda expression.</returns> /// <exception cref="System.InvalidOperationException">Thrown if the constructor is invalid.</exception> private Expression <Func <TParent, TApplication, Action <TOutput>, TOutput> > CreateNewItemExpression(Type controlType) { var applicationParameter = Expression.Parameter(typeof(TApplication), "application"); var applicationArgument = new ExpressionData(applicationParameter, typeof(TApplication), "application"); var parentParameter = Expression.Parameter(typeof(TParent), "parent"); var parentArgument = new ExpressionData(parentParameter, typeof(TParent), "rootContext"); var controlVariable = Expression.Variable(controlType); var controlData = new ExpressionData(controlVariable, controlType, controlType.Name); var context = new ControlBuilderContext(applicationArgument, parentArgument, controlData); var constructor = this.GetConstructor(controlType, context); if (constructor == null) { throw this.CreateConstructorException(null, controlType); } var actionParameter = Expression.Parameter(typeof(Action <TOutput>), "action"); // Spin though properties and make an initializer for anything we can set that has an attribute var pageMethodInfo = new Action <TOutput, Action <TOutput> >(this.AssignWindowAttributes).GetMethodInfo(); var expressions = new List <Expression> { Expression.Assign(controlVariable, Expression.New(constructor.Item1, constructor.Item2)), Expression.Call( Expression.Constant(this), pageMethodInfo, Expression.Convert(controlVariable, typeof(TOutput)), actionParameter) }; this.MapObjectProperties(expressions, controlType, context); expressions.Add(controlVariable); var methodCall = Expression.Block(new[] { controlVariable }, expressions); return(Expression.Lambda <Func <TParent, TApplication, Action <TOutput>, TOutput> >(methodCall, parentParameter, applicationParameter, actionParameter)); }
/// <summary> /// Gets the constructor parameter for the given type. /// </summary> /// <param name="parameterType">Type of the parameter to fill.</param> /// <param name="parentArgument">The parent argument.</param> /// <param name="rootLocator">The root locator argument if different from the parent.</param> /// <returns>The constructor information that matches.</returns> protected virtual Expression FillConstructorParameter(Type parameterType, ExpressionData parentArgument, ExpressionData rootLocator) { return(typeof(TParent).IsAssignableFrom(parameterType) ? parentArgument.Expression : null); }