It is not easy for me to build constructor.
I am trying to make second constructor of the code
public class Sample
{
public Sample Parent { get; set; }
public Sample(Sample parent)
{
Parent = parent;
Children = new ObservableTestCollection<Sample>(this);
}
public Sample(Sample parent, IEnumerable<Sample> source)
{
Parent = parent;
Children = new ObservableTestCollection<Sample>(this, source);
}
public ObservableTestCollection<Sample> Children { get; set; }
}
And the source of ObservableTestCollection as follows:
public class ObservableTestCollection<T> : ObservableCollection<T>
{
public T Parent;
public ObservableTestCollection(T parent):this(parent, Enumerable.Empty<T>())
{
}
public ObservableTestCollection(T parent, IEnumerable<T> source): base(source)
{
Parent = parent;
}
}
And the constructor builder I wrote is as follows:
//first constructor
var obsCtor1 = typeOfCts.GetConstructors().First(c => c.GetParameters().Length == 1);
obsCtor1 = TypeBuilder.GetConstructor(genericTypeOfCts, obsCtor1);
var constructorParameters = new Type[] { typeBuilder };
var ctorBuilder = typeBuilder.DefineConstructor(MethodAttributes.Public, CallingConventions.HasThis, constructorParameters);
il = ctorBuilder.GetILGenerator();
il.Emit(OpCodes.Ldarg_0);
il.Emit(OpCodes.Call, typeof(object).GetConstructor(Type.EmptyTypes));
il.Emit(OpCodes.Ldarg_0);
il.Emit(OpCodes.Ldarg_1);
il.Emit(OpCodes.Call, setParentMethod);
il.Emit(OpCodes.Ldarg_0);
il.Emit(OpCodes.Ldarg_0);
il.Emit(OpCodes.Newobj, obsCtor1);
il.Emit(OpCodes.Call, setChildrenMethod);
il.Emit(OpCodes.Ret);
//second constructor
var obsCtor2 = typeOfCts.GetConstructors().First(c => c.GetParameters().Length == 2);
obsCtor2 = TypeBuilder.GetConstructor(genericTypeOfCts, obsCtor2);
var ctorParam = typeOfCts.MakeGenericType(typeBuilder);
constructorParameters = new Type[] { typeBuilder, ctorParam };
ctorBuilder = typeBuilder.DefineConstructor(MethodAttributes.Public, CallingConventions.HasThis, constructorParameters);
il = ctorBuilder.GetILGenerator();
il.Emit(OpCodes.Ldarg_0);
il.Emit(OpCodes.Call, typeof(object).GetConstructor(Type.EmptyTypes));
il.Emit(OpCodes.Ldarg_0);
il.Emit(OpCodes.Ldarg_1);
il.Emit(OpCodes.Call, setParentMethod);
il.Emit(OpCodes.Ldarg_0);
il.Emit(OpCodes.Ldarg_0);
il.Emit(OpCodes.Ldarg_2);
il.Emit(OpCodes.Newobj, obsCtor2);
il.Emit(OpCodes.Call, setChildrenMethod);
il.Emit(OpCodes.Ret);
Type type = typeBuilder.CreateType();
var obj1 = Activator.CreateInstance(type, new object[] { null });
var obj2 = Activator.CreateInstance(type, obj1);
assemblyBuilder.Save(assemblyFileName);
var children = (IList)obj2.GetType().GetProperty(selfRefDerivedCollectionName).GetValue(obj2, null);
((INotifyCollectionChanged)children).CollectionChanged += Program_CollectionChanged;
var obj3 = Activator.CreateInstance(type, new object[] { null });
children.Add(obj3);
var listOf = typeof(List<>);
var listOfType = listOf.MakeGenericType(type);
var list =(IList) Activator.CreateInstance(listOfType);
obj1 = Activator.CreateInstance(type, new object[] { null });
list.Add(obj1);
obj1 = Activator.CreateInstance(type, new object[] { null });
list.Add(obj1);
var obj4 = Activator.CreateInstance(type, list);
Can somebody help me to find out what's wrong with my code.
I found that the problem was not in building second constructor, but was in making instance of generic type.
I updated as follows: