The editor for PropertyDictionaryMultiple is registered for TargetType = typeof(ItemCollection<string>), so you have two options:
Hi Quan,
Thanks for the quick response, but unfortunately it doesn't work. I have also reproduced the issue in quick silver, example code below
Works as expected (Items rendered out as a collection of checkboxes)
[CatalogContentType(
GUID = "550ebcfc-c989-4272-8f94-c6d079f56181",
MetaClassName = "FashionProduct",
DisplayName = "Fashion product",
Description = "Display fashion product")]
public class FashionProduct : ProductContent
{
...
[Searchable]
[IncludeInDefaultSearch]
[BackingType(typeof(PropertyDictionaryMultiple))]
[Display(Name = "Available Colors", Order = 6)]
public virtual ItemCollection<string> AvailableColors { get; set; }
}
Failing example (Text input displayed)
[CatalogContentType(
GUID = "550ebcfc-c989-4272-8f94-c6d079f56181",
MetaClassName = "FashionProduct",
DisplayName = "Fashion product",
Description = "Display fashion product")]
public class FashionProduct : ProductContent
{
public virtual SpecificationsBlock Specifications { get; set; }
}
[ContentType(
DisplayName = "Specifications Block",
GUID = "73E57D6A-9196-4C84-B76C-8CE397C5CC04",
Description = "Specifications Block",
AvailableInEditMode = false)]
public class SpecificationsBlock : BlockData
{
...
[Searchable]
[IncludeInDefaultSearch]
[BackingType(typeof(PropertyDictionaryMultiple))]
[Display(Name = "Available Colors", Order = 6)]
public virtual ItemCollection<string> AvailableColors { get; set; }
}
Hmm, you would need this attribute as well
[UIHint(SystemUiHint.DictionaryMultipleSelector)]
By using ItemCollection<string> the framework will add the UIHint for you, but not on a nested property like that
Hi Quan,
Adding this attribute works, but exposes a bug I think.
When the property is added to the block, a metadata/dictionary is created with the name 'EpiBlock_<Blockname>_<PropertyName>' But the editor control tries to load the data, it expects to use the <PropertyName>.
In the example above you can see the metadata created by the system, and the one I created to stop the editor crashing.
Logs below
System.ArgumentException: Could not load the meta field 'Connectors'.
at EPiServer.Commerce.Shell.UIDescriptors.EditorDescriptors.SelectionFactories.DictionarySelectionFactory.LoadDictionary(String metaFieldName)
at EPiServer.Commerce.Shell.UIDescriptors.EditorDescriptors.SelectionFactories.DictionarySelectionFactory.<GetSelections>d__1.MoveNext()
at EPiServer.Shell.UI.Rest.DefaultMetadataStoreModelCreator.GetSelections(ExtendedMetadata metadata, MetadataStoreModel metadataDTO, ISelectionFactory[] selectionFactories)
at EPiServer.Shell.UI.Rest.DefaultMetadataStoreModelCreator.CreateFromModelMetadata(ExtendedMetadata metadata, LocalizationService localizationService, UIDescriptorRegistry uiDescriptorRegistry, ISelectionFactory[] selectionFactories, Boolean alwaysCreateChildProperties)
at EPiServer.Shell.UI.Rest.DefaultMetadataStoreModelCreator.ExtractMetadataFromProperties(ExtendedMetadata metadata, MetadataStoreModel MetadataStoreModel, LocalizationService localizationService, UIDescriptorRegistry uiDescriptorRegistry, ISelectionFactory[] selectionFactories)
at EPiServer.Shell.UI.Rest.DefaultMetadataStoreModelCreator.CreateFromModelMetadata(ExtendedMetadata metadata, LocalizationService localizationService, UIDescriptorRegistry uiDescriptorRegistry, ISelectionFactory[] selectionFactories, Boolean alwaysCreateChildProperties)
at EPiServer.Shell.UI.Rest.DefaultMetadataStoreModelCreator.ExtractMetadataFromProperties(ExtendedMetadata metadata, MetadataStoreModel MetadataStoreModel, LocalizationService localizationService, UIDescriptorRegistry uiDescriptorRegistry, ISelectionFactory[] selectionFactories)
at EPiServer.Shell.UI.Rest.DefaultMetadataStoreModelCreator.CreateFromModelMetadata(ExtendedMetadata metadata, LocalizationService localizationService, UIDescriptorRegistry uiDescriptorRegistry, ISelectionFactory[] selectionFactories, Boolean alwaysCreateChildProperties)
at EPiServer.Shell.UI.Rest.DefaultMetadataStoreModelCreator.Create(ModelMetadata metadata)
at EPiServer.Shell.UI.Rest.MetadataStore.Get(String id, String modelAccessor)
at lambda_method(Closure , ControllerBase , Object[] )
at System.Web.Mvc.ControllerActionInvoker.InvokeActionMethod(ControllerContext controllerContext, ActionDescriptor actionDescriptor, IDictionary`2 parameters)
at System.Web.Mvc.Async.AsyncControllerActionInvoker.<>c.<BeginInvokeSynchronousActionMethod>b__9_0(IAsyncResult asyncResult, ActionInvocation innerInvokeState)
at System.Web.Mvc.Async.AsyncResultWrapper.WrappedAsyncResult`2.CallEndDelegate(IAsyncResult asyncResult)
at System.Web.Mvc.Async.AsyncControllerActionInvoker.EndInvokeActionMethod(IAsyncResult asyncResult)
at System.Web.Mvc.Async.AsyncControllerActionInvoker.AsyncInvocationWithFilters.<>c__DisplayClass11_0.<InvokeActionMethodFilterAsynchronouslyRecursive>b__0()
at System.Web.Mvc.Async.AsyncControllerActionInvoker.AsyncInvocationWithFilters.<>c__DisplayClass11_2.<InvokeActionMethodFilterAsynchronouslyRecursive>b__2()
at System.Web.Mvc.Async.AsyncControllerActionInvoker.AsyncInvocationWithFilters.<>c__DisplayClass11_2.<InvokeActionMethodFilterAsynchronouslyRecursive>b__2()
at System.Web.Mvc.Async.AsyncControllerActionInvoker.EndInvokeActionMethodWithFilters(IAsyncResult asyncResult)
at System.Web.Mvc.Async.AsyncControllerActionInvoker.<>c__DisplayClass3_6.<BeginInvokeAction>b__4()
at System.Web.Mvc.Async.AsyncControllerActionInvoker.<>c__DisplayClass3_1.<BeginInvokeAction>b__1(IAsyncResult asyncResult)
at System.Web.Mvc.Async.AsyncControllerActionInvoker.EndInvokeAction(IAsyncResult asyncResult)
at EPiServer.Shell.Services.Rest.RestControllerBase.EndExecute(IAsyncResult asyncResult)
True. Now it's probably a déjà vu, but that was probably the reason that we didn't add the UIHint automatically for the nested properties... I will need to check with the team
I checked with the team, the decision was made some time ago that we only support the dictionary types in block at API level, but not UI level, due to complexity. So ...
Hi Quan,
Is this on the backlog to get resolved?
It may be worth updating the documentation around the limitations of blocks within commerce. There are a number of areas where the behaviour isn't the same as the CMS.
Thanks
Hi,
I have created a Block which I am using on a Commerce Product Node and am running into issues when adding a property and setting the backing type to be 'PropertyDictionaryMultiple'. The editor is not rendering correctly, I am just seeing a text input, rather than a collection of check boxes.
When I move the same property down to the Product, it is rendered as expected.
Example below
[BackingType(typeof(PropertyDictionaryMultiple))]
[Display(Name = "Connectors2", Order = 7)]
[CultureSpecific]
public virtual PropertyList<string> Connectors2 { get; set; }
I am using Commerce '13.6.0'.
Looking at other posts it seems that this was reported and fixed in commerce 12.
Thanks