我有答案(當然我是有年代久遠,但我記得我張貼了這個問題)。這是一個來自幾十億片斷和我自己大腦的破解代碼怪物,所以我不能將每個人歸因於它。我打算放棄它。因爲我覺得這很棒。即使沒有人關心:
它的用途: - DLR - 一點反思 - 一點IL建設。
也許應該將所有這一切都爲博客文章的地方,但我不保持一個博客。
這是用於由視圖模型稱爲視圖創建數據的代碼。
public IEnumerable<dynamic> CreateData(ObservableCollection<ReportFieldVm> reportFields)
{
// Find the length of the array.
var size = reportFields.Count;
// Create matrix.
var b = new int[size, size];
// Random for the values.
var rand = new Random((int)DateTime.Now.Ticks);
// Build the symmetric matrix.
for (var i = 0; i < size; i++)
{
for (var j = 0; j < size; j++)
{
if (i == j)
{
b[i,j] = rand.Next(0, 100);
}
else
{
var a = rand.Next(0, 100);
b[i,j] = a;
b[j,i] = a;
}
}
}
// Define the assembly to add out new type to.
var asmName = new AssemblyName("DummyAssembly");
var ab = AppDomain.CurrentDomain.DefineDynamicAssembly(asmName, AssemblyBuilderAccess.Run);
var mb = ab.DefineDynamicModule("DummyModule");
// Define our type.
var d = mb.DefineType("DummyType", TypeAttributes.Public);
const MethodAttributes GetSetAttr = MethodAttributes.Public | MethodAttributes.SpecialName | MethodAttributes.HideBySig;
// Define all the fields for the new type.
foreach (var rf in reportFields.OrderBy(rf => rf.SelectOrder))
{
var propertyName = rf.FieldName;
var field = d.DefineField("m_" + propertyName, typeof(int), FieldAttributes.Private);
var property = d.DefineProperty(propertyName, PropertyAttributes.HasDefault, typeof(int), null);
var dGetAccessor = d.DefineMethod("get_" + propertyName, GetSetAttr, typeof(int), Type.EmptyTypes);
var numberGetIl = dGetAccessor.GetILGenerator();
numberGetIl.Emit(OpCodes.Ldarg_0);
numberGetIl.Emit(OpCodes.Ldfld, field);
numberGetIl.Emit(OpCodes.Ret);
var dSetAccessor = d.DefineMethod("set_" + propertyName, GetSetAttr, null, new Type[] { typeof(int) });
var numberSetIl = dSetAccessor.GetILGenerator();
numberSetIl.Emit(OpCodes.Ldarg_0);
numberSetIl.Emit(OpCodes.Ldarg_1);
numberSetIl.Emit(OpCodes.Stfld, field);
numberSetIl.Emit(OpCodes.Ret);
property.SetGetMethod(dGetAccessor);
property.SetSetMethod(dSetAccessor);
}
// Create the type.
var dummyType = d.CreateType();
var array = new List<dynamic>();
// Convert the matrix into the array of the dynamic.
for (var i = 0; i < size; i++)
{
var obj = Activator.CreateInstance(dummyType);
int j = 0;
foreach (var rf in reportFields.OrderBy(rf => rf.SelectOrder))
{
var type = obj.GetType();
var prop = type.GetProperty(rf.FieldName);
prop.SetValue(obj, b[j, i], null);
j++;
}
array.Add(obj);
}
return array;
}
這是綁定在視圖中調用的視圖的代碼。
其中:
_dynamicReportPreview
是在XAML命名的網格。
ViewModel
是公開在視圖構造函數中設置視圖的DataContext
的屬性。
private void BuildPreviewGridColumns()
{
if (_dynamicReportPreview == null)
return;
_dynamicReportPreview.Columns.Clear();
var initialFields = ViewModel.ReportFields.OrderBy(rf => rf.SelectOrder);
foreach (var rf in initialFields)
{
var col = new Column
{
ColumnName = rf.FieldName,
Binding = new Binding(rf.FieldName)
};
_dynamicReportPreview.Columns.Add(col);
if (!rf.IsVisible)
{
col.Visible = false;
}
}
}
我在下面回答我自己的問題。這應該可能是一篇博客文章,因爲參與此事的每個人都是我。但是那裏有一些非常有用的片段。值得一讀,我猜。 – tigerswithguitars 2013-03-12 15:27:30
嘿,過去我......你可以使用ExpandoObject而不是創建一個新類型? http://blogs.msdn.com/b/csharpfaq/archive/2009/10/01/dynamic-in-c-4-0-introducing-the-expandoobject.aspx – tigerswithguitars 2013-12-12 10:17:48