none
Silverlight General FAQ: Bagaimana cara flexible binding pada (untyped) sumber data? (Part 2) RRS feed

  • Diskusi Umum

  • Sekarang kita akan mendefinisikan metadata. Kita memerlukan sebuah Dictionary untuk menyimpan nama kolom dengan typenya. Setiap metadata akan berisi daftar rows. Setiap row memiliki Dictionary untuk memetakan nilai untuk column. Kita akan membuat struktur data sebagai berikut:

     

    public class Metadata

    {

             public Dictionary<string, Type> Columns { get; set; }

             public List<MetadataRow> Rows { get; set; }

    }

     

    public class MetadataRow

    {

             public Dictionary<string, object> ColumnValues { get; set; }

    }

     

     

    Misalkan kita memiliki metadata, yang harus dilakukan selanjutnya adalah untuk membuat dynamic type berdasarkan informasi yang disediakan dalam metadata. Kita akan menggunakan emitting untuk menghasilkan type. Pertama, buat sebuah type bernama DataSource. Kemudian tambahkan properti sesuai dengan kolom didefinisikan dalam metadata. Untuk informasi lebih lanjut tentang cara untuk membuat jenis dinamis menggunakan metode emitting, lihat http://msdn.microsoft.com/en-us/library/4xxf1410(VS.95).aspx

     

    AppDomain myDomain = AppDomain.CurrentDomain;

    AssemblyName myAsmName = new AssemblyName("MyAssembly");

    AssemblyBuilder myAssembly = myDomain.DefineDynamicAssembly(myAsmName,

    AssemblyBuilderAccess.Run);

    ModuleBuilder myModule = myAssembly.DefineDynamicModule(myAsmName.Name);

    TypeBuilder myType = myModule.DefineType("DataSource", TypeAttributes.Public);

    foreach (string columnName in metadata.Columns.Keys)

    {

             Type properyType = metadata.Columns[columnName];

             FieldBuilder exField = myType.DefineField("_" + columnName, properyType, FieldAttributes.Private);

             PropertyBuilder exProperty = myType.DefineProperty(columnName, PropertyAttributes.None,

    properyType, Type.EmptyTypes);

             //Get

             MethodBuilder exGetMethod = myType.DefineMethod("get_" + columnName,

    MethodAttributes.Public, properyType, Type.EmptyTypes);

             ILGenerator getIlgen = exGetMethod.GetILGenerator();

    //IL for a simple getter:

             //ldarg.0

             //ldfld int32 SilverlightClassLibrary1.Class1::_Age

             //ret

             getIlgen.Emit(OpCodes.Ldarg_0);

             getIlgen.Emit(OpCodes.Ldfld, exField);

             getIlgen.Emit(OpCodes.Ret);

             exProperty.SetGetMethod(exGetMethod);

             //Set

             MethodBuilder exSetMethod = myType.DefineMethod("set_" + columnName,

    MethodAttributes.Public, null, new Type[] { properyType });

             ILGenerator setIlgen = exSetMethod.GetILGenerator();

             //IL for a simple setter:

             //ldarg.0

             //ldarg.1

             //stfld int32 SilverlightClassLibrary1.Class1::_Age

             //ret

             setIlgen.Emit(OpCodes.Ldarg_0);

             setIlgen.Emit(OpCodes.Ldarg_1);

             setIlgen.Emit(OpCodes.Stfld, exField);

             setIlgen.Emit(OpCodes.Ret);

             exProperty.SetSetMethod(exSetMethod);

    }

    Type finished = myType.CreateType();

     

    Setelah property dan type diciptakan, sekarang kita perlu membuat satu instance dari DataSource untuk setiap baris, dan mengisi nilai-nilainya dengan setting properti, dan akhirnya menetapkan ItemsSource datagrid itu.

     

    ObservableCollection<object> source = new ObservableCollection<object>();

    foreach (MetadataRow row in metadata.Rows)

    {

             object item = Activator.CreateInstance(finished);

             foreach (string columnName in metadata.Columns.Keys)

             {

                       MethodInfo method = finished.GetMethod("set_" + columnName);

                       method.Invoke(item, new object[] { row.ColumnValues[columnName] });

             }

             source.Add(item);

    }

    this.dg.ItemsSource = source;

     

    Sekarang anda dapat menguji kode di atas, sebagai contoh, kita hanya mengisi beberapa data palsu. Dalam skenario nyata, anda mungkin akan mencoba untuk membiarkan user menentukan kolom mereka sendiri, values, serialize metadata untuk xml, memanggil layanan REST dan menyimpannya di server.

     

    Metadata metadata = new Metadata();

    metadata.Columns = new Dictionary<string, Type>();

    metadata.Columns.Add("Column1", typeof(string));

    metadata.Columns.Add("Column2", typeof(int));

    metadata.Columns.Add("Column3", typeof(bool));

    metadata.Rows = new List<MetadataRow>();

    Dictionary<string, object> row1Values = new Dictionary<string, object>();

    row1Values.Add("Column1", "abc");

    row1Values.Add("Column2", 2);

    row1Values.Add("Column3", true);

    metadata.Rows.Add(new MetadataRow() { ColumnValues = row1Values });

    Dictionary<string, object> row2Values = new Dictionary<string, object>();

    row2Values.Add("Column1", "xyz");

    row2Values.Add("Column2", 20);

    row2Values.Add("Column3", true);

    metadata.Rows.Add(new MetadataRow() { ColumnValues = row2Values });

    Dictionary<string, object> row3Values = new Dictionary<string, object>();

    row3Values.Add("Column1", null);

    row3Values.Add("Column2", 0);

    row3Values.Add("Column3", false);

    metadata.Rows.Add(new MetadataRow() { ColumnValues = row3Values });

     


    Agnes Sannie [MSFT]
    MSDN Community Support | Feedback to us
    Get or Request Code Sample from Microsoft
    Please remember to mark the replies as answers if they help and unmark them if they provide no help.
    Rabu, 22 Juni 2011 06.08
    Moderator