specifying the order of Content Fields (in Migrations.cs or placement.info)?

Topics: Customizing Orchard, Writing modules
Mar 18, 2013 at 8:31 AM
Hi guys,

I'm working on a custom content type delivered via a module, and having issues specifying a specific order in which the fields need to be displayed on the content type.

I've tried the following:
  • I understand there's the Edit Placement function / code, so I took a look in AdminController.cs to see if there was anything I could use in here, but it looks like it uses an extension method within the Orchard.ContentTypes module - am I supposed to add a reference and use these methods?
  • I looked into the BlogPosts module, and noticed the placement.info specified the ordering of the fields for Admin / Summary views; but I'm not sure if this only works for Content Part properties, or for fields themselves, because it didn't seem to work for me.
  • I tried using the .WithLocation method within AlterPartDefinition, but that didn't seem to catch either (not sure if I had the zone name correct or not, or if it reads fields differently to other placeable things)
Here's a look at the code / placement.info that doesn't quite work for me:
    public class Migrations : DataMigrationImpl

        public int Create()

            //the part name has to match the Content Type name if you're adding Fields
              builder => builder                        
                            .WithField("StartDate", cfg => cfg
                                .WithDisplayName("Start Date")
                                .WithSetting("DateTimeFieldSettings.Display", "DateOnly")
                                .WithSetting("DateTimeFieldSettings.Required", "true"))
                            .WithField("StartTime", cfg => cfg
                                .WithDisplayName("Start Time")
                                .WithSetting("DateTimeFieldSettings.Display", "TimeOnly"))
                            .WithField("EndDate", cfg => cfg
                                .WithDisplayName("End Date")
                                .WithSetting("DateTimeFieldSettings.Display", "DateOnly"))
                            .WithField("EndTime", cfg => cfg
                                .WithDisplayName("End Time")
                                .WithSetting("DateTimeFieldSettings.Display", "TimeOnly"))
                            .WithField("Logistics", cfg => cfg
                                .WithSetting("TextFieldSettings.Flavor", "html"))
                            .WithField("ContactUs", cfg => cfg
                                .WithDisplayName("Contact Us")
                                .WithSetting("TextFieldSettings.Flavor", "textarea"))   

//this WithLocation doesn't seem to work - expected the StartTime and Logistics to be next to each other separate from the rest of the fields...
  //.WithLocation(new Dictionary<string,ContentLocation>{  
                            //{"Fields_DateTime-StartTime", new ContentLocation { Zone="Content", Position="10.0" }},
                            //{"Fields_Common_Text-Logistics", new ContentLocation { Zone="Content", Position="10.10" }} })


            // add parts to ContentType
                , cfg =>
                        .DisplayedAs("My CT")                        

            return 1;
And the placement.info,
  <!-- Customize where the shapes are rendered -->

  <Match ContentType="MyCT">
    <Match DisplayType="Detail">     
      <Place Fields_DateTime-StartDate="Content:10.0"
    <Match DisplayType="DetailAdmin">
      <Place Fields_DateTime-StartDate="Content:10.0"
    <Match DisplayType="Summary"> <!--todo: fix rollups-->
            <Place Fields_DateTime-StartDate="Content:10.0"
    <Match DisplayType="SummaryAdmin">    <!--todo: fix rollups-->
            <Place Fields_DateTime-StartDate="Content:10.0"

In a nutshell, what's the recommended way to specify the ordering of fields for both the Admin and Display side of pages, for a content type deployed from a custom module?
Mar 18, 2013 at 11:32 AM
I think for Admin the best way is to use the Placement UI. If that doesn't work, please file a bug with repro steps.
For Display, I'd say Placement.info is the way to go.

Keep in mind that when you are working with a Placement.info file from your module that places shapes emitted from other modules, there's no guarantee that these "3rd party" shapes are placed using your placement.info.
So you have to either use the Placement.info file from the theme (which is generally the recommended way, since themes take precedence with regards to placement), or add the modules whose shapes you are trying to place from your module's Placement.info to the list of dependencies in your module's manifest.

I believe that the latter approach works for Editor (Admin) shapes as well, but I haven't tested that myself.
Mar 18, 2013 at 3:24 PM
Hi sfmakywalker,

so by placement UI, you mean the Edit Placement link when you're editing the content type, correct? Is there an example / any documentation on how I can work with it programmatically (IE in the migrations.cs file, after the content type is created?)
Mar 18, 2013 at 11:55 PM
Yeah that's the one.

I don't know of any documentation on this, so I would just dive into the code that is responsible for this feature and see how they do it.