Wednesday 3 June 2009

A Great Buried Sample in Dynamic Data Preview 4 – Dynamic Data Futures

I just thought I’d mention this find ad David Ebbo mentioned overriding MetaTable to get at the table.GetScaffoldColumns() method, and then I found the Dynamic Data Futures sample inside of Preview 4 (which had a billing of being the Futures sample updated to work with Preview 4) and in side the it I found the CustomMetaClasses folder:

The CustomMetaClasses folder

Figure 1 – The CustomMetaClasses folder

This of course give you the sample you need to do this your self my plan is to use this sample to make a MetaTable Class that I can pass in a Lambda function to do all my column generation without ever having to add IAutoFieldGenerator to the page (which in .Net 4.0 will not work on the Details, Edit and Insert pages as they are to be based on FormView to accomodate EntityTemplates).

public class Global : System.Web.HttpApplication
{
    private static MetaModel s_defaultModel = new CustomMetaModel();
    public static MetaModel DefaultModel
    {
        get
        {
            return s_defaultModel;
        }
    }

    public static void RegisterRoutes(RouteCollection routes)
    {
        DefaultModel.RegisterContext(typeof(NorthwindDataContext), new ContextConfiguration()
        {
            ScaffoldAllTables = true,
            MetadataProviderFactory = (type => new InMemoryMetadataTypeDescriptionProvider(type,
new AssociatedMetadataTypeTypeDescriptionProvider(type))) });

Listing 1 – Adding a DefaultModel based on CustomMetaModel from the CustomMetaClasses folder

Listing 1 shows the addition of the CustomMetaModel to the Global.asax allowing you to override the Meta Classes in one place this is cool.

Thanks again ASP.Net Team HappyWizard

9 comments:

Anonymous said...

Glad you found this useful! Granted, we haven't done a good job advertising this feature :)

Stephen J. Naughton said...

Yes I love this feaure.

Steve :D

Anonymous said...

So does this mean the whole IAutoFieldGenerator way of extending Dynamic Data is basically kaput? I was just trying to use your HideInColumnAttribute ideas and ran smack into the FormView issue. So I should try to figure out the CustomMetaClasses methodology instead? I was going to try to avoid using anything in the Futures part of Preview 4, only going so far as the VNext stuff to be on the cautious side. I guess I have no choice now but to go "whole hog"?

Stephen J. Naughton said...

Well in .Net 4.0 yes as now only the List page supports IAutoFieldGenerator, You could also do field generation in Default.ascx EntityTemplate but this only works for Details, Edit and Insert.

Steve :D

Adrian said...

Hi Steve,
Your HideInColumnAttribute ideas can be easily adapted to work with Dynamic Data Preview 4.

So here’s the fields manger code:


#region FieldManager Members
/// Hide/Unhide the fields.
public IDictionary<string, MetaColumn> ScaffoldColumnsForTemplate(PageTemplate templatePage)
{
var columnForTemplate = new Dictionary<string, MetaColumn>();
//
foreach (var column in metaTable.Columns)
{
// carry on the loop at the next column
// if scaffold table is set to false or DenyRead
if (column.Scaffold && column.IsHidden(templatePage))
{
// do not scaffold
column.Scaffold = false;
}
else if (!column.Scaffold && !column.IsHidden(templatePage) && !column.IsLongString && !column.IsForeignKeyComponent && !column.IsPrimaryKey)
{
// scaffold
column.Scaffold = true;
}

// store
if (column.Scaffold)
columnForTemplate.Add(column.Name, column);
}
// done
return columnForTemplate;
}
#endregion

And in the page templates (Ex. List.aspx.cs):

protected void Page_Init(object sender, EventArgs e)
{
table = DynamicDataRouteHandler.GetRequestMetaTable(Context);

// hide the columns
using (HideColumnFieldsManager fieldsManager = new HideColumnFieldsManager(ref table))
{
fieldsManager.ScaffoldColumnsForTemplate(PageTemplate.List);
}

GridView1.SetMetaTable(table, table.GetColumnValuesFromRoute(Context));

GridDataSource.EntityTypeName = table.EntityType.AssemblyQualifiedName;

if (table.EntityType != table.RootEntityType)
{
GridQueryExtender.Expressions.Add(new OfTypeExpression(table.EntityType));
}
}

The Metadata files:

[HideColumnIn(PageTemplate.List)]
public string EmailAddress { get; set; }


It works fine for me. What do you think?

Thank you,
Adrian

Stephen J. Naughton said...

Looks good to me...

Steve :D

Anonymous said...

Hi Steve.

I'm using VS2010 Beta2 and have gotten the MetaTable class extenions working so that I can I can selectively hide columns on the edit/insert/details pages.

I still have the IAutoFieldGenerator (from one of your earlier examples) working as well for the DD list pages.

However, you mentioned above that you plan on coding a method where you will use the MetaTable extentions and not have to use the IAutoFieldGenerator method.

Could you give me a brief summary of how you might go about tackling that?

Thanks!

-Bob (beeps4848)

Anonymous said...

Hi (again). :-)

Scratch my last comment because I just saw your new article here: http://csharpbits.notaclue.net/2009/06/great-buried-sample-in-dynamic-data.html

Good stuff as usual!

-Bob

Stephen J. Naughton said...

Hi Bob see:
http://csharpbits.notaclue.net/2010/02/new-way-to-do-column-generation-in.html
http://csharpbits.notaclue.net/2010/02/grouping-field-on-details-edit-and.html
http://csharpbits.notaclue.net/2010/02/displayattribute-prompt-or-watermark-in.html