Link Collection Module - adding a select drop-down input in a Create link popup form

Min
Min
Vote:
 

For version: 11.15.0.0 above

I found a few good documents about how to add a hyperlink and a simple text field. 

But not a select dropdown input. 

Currently, on the form, Link name/Text, Link title, Open in, and links options. 

Would like to add additional select dropdown field on the below form. 

Enlighten me.
Thanks.

#280218
Edited, May 12, 2022 9:47
Vote:
 

Hi Min,

Are you trying to update a current property? or is this a new property you have created?

I have found that using the LinkItemCollection has it's limitations.

What you are trying to achieve can be done, it just requires some more effort.

Therefore we want to work smarter Marija has written an approach to extending the LinkItemCollection.

Another alternative is to use the PropertyList<T>  this way you can create the model with all the options easily and provide this to the editor.

Paul

#280376
May 16, 2022 11:09
Min
Vote:
 

Hi Paul

Thanks. I am trying to update the current property. Yes, it has limitations. 

But one of my forms use the LinkItemCollection since the project started but now, want to add one more additional field on the same form as we like to keep editor's data entry workflow as it is now.

I guess, I would need to wait EPiServer to fix it.

Thanks.

#280456
May 17, 2022 13:07
Vote:
 

Hi Min,

You can try with the workaround

1. Custom editor descriptor

[EditorDescriptorRegistration(TargetType = typeof(LinkItemCollection), UIHint = "CustomLinkItemCollection")]
    public class CustomLinkItemCollectionEditorDescriptor : LinkCollectionEditorDescriptor
    {
        public CustomLinkItemCollectionEditorDescriptor(IEnumerable<IContentRepositoryDescriptor> contentRepositoryDescriptors) : base(contentRepositoryDescriptors)
        {
            ClientEditingClass = "alloy/editors/CustomItemCollectionEditor";
        }

        public override void ModifyMetadata(ExtendedMetadata metadata, IEnumerable<Attribute> attributes)
        {
            ClientEditingClass = "alloy/editors/CustomItemCollectionEditor";
            base.ModifyMetadata(metadata, attributes);

            var options = new
            {
                ItemModelType = "alloy/editors/models/CustomLinkItemModel",
                CustomTypeIdentifier = typeof(CustomLinkModel).FullName.ToLower()
            };

            var commandOptions = new
            {
                DialogContentParams = new
                {
                    ModelType = typeof(CustomLinkModel).FullName.ToLower(),
                    BaseClass = "epi-link-item"
                }
            };

            metadata.OverlayConfiguration["modelParams"] = options;
            metadata.EditorConfiguration["itemModelType"] = options.ItemModelType;
            metadata.EditorConfiguration["customTypeIdentifier"] = options.CustomTypeIdentifier;
            metadata.EditorConfiguration["commandOptions"] = commandOptions;
        }
    }

2. Implement your custom model with custom option (dropdown, selection)

public class CustomLinkModel : LinkModel
    {
        [Display(Name = "Custom Option")]
        [SelectOne(SelectionFactoryType = typeof(CustomSelectionFactory))]
        public string CustomOption { get; set; }
    }

    public class CustomSelectionFactory : ISelectionFactory
    {
        public IEnumerable<ISelectItem> GetSelections(ExtendedMetadata metadata)
        {
            return new[]
            {
                new SelectItem
                {
                    Text = "aaaaaa",
                    Value = "1"
                },
                new SelectItem
                {
                    Text = "bbbbb",
                    Value = "2"
                },
                new SelectItem
                {
                    Text = "ccccc",
                    Value = "3"
                },
                new SelectItem
                {
                    Text = "ddddd",
                    Value = "4"
                },
                new SelectItem
                {
                    Text = "eeeee",
                    Value = "5"
                },
            };
        }
    }

3. Inherit and override client editor

define([
    "dojo/_base/declare",
    "alloy/editors/models/CustomLinkItemModel",
    "epi-cms/contentediting/editors/ItemCollectionEditor"
], function (
    declare,
    CustomLinkItemModel,
    ItemCollectionEditor
) {
    return declare([ItemCollectionEditor], {

    });
});

4. Inherit and overide client item model

define([
    "dojo/_base/declare",
    "epi-cms/contentediting/viewmodel/LinkItemModel"
], function (
    declare,
    LinkItemModel
) {
    return declare([LinkItemModel], {
        customOption: null,
        _customOptionGetter: function () {
            return this.customOption;
        },

        postCreate: function () {
            this.inherited(arguments);
        },

        serialize: function () {
            var baseValue = this.inherited(arguments);

            return Object.assign(baseValue, {
                attributes: {
                    customOption: this.customOption
                }
            });
        },

        parse: function () {
            this.inherited(arguments);

            if (!this.customOption && this.attributes) {
                this.customOption = this.attributes?.customOption;
            }
        }
    });
})

Sceenshot

#280759
Edited, May 23, 2022 8:29
Paul McGann (Netcel) - May 23, 2022 8:32
Nice work here
Mark Stott - May 26, 2022 11:39
That is pretty cool!
Aneta Petryla - Jan 04, 2023 7:22
Generally it works, but I have one problem to limit properties which I want to override. When I placed UIHint("CustomLinkItemCollection") attribute to the property LinkItemCollection I can't edit block it's blank in edit mode, so sth is wrong (the editorDescriptor is called correctly). Without using UIHInt every property is overridden well.
Ha Bui - Jan 04, 2023 12:26
Hi @Aneta Patryla, I guess we should have some console errors?
Aneta Petryla - Jan 04, 2023 12:32
Hi @Ha Bui. Nothing special in console errors. I've used wrong editing class, now UIHint works :) But I have another question, this option is added as additional not required field (dropdown).
1) How to add new option as radio button (like Page or Media being ContentReference type)
OR
2) How to add this custom field only under "Page" option (like Remaining Url field)?

Is one of this thing possible to implement or too many js class to override?
Ha Bui - Jan 04, 2023 15:06
Hi Aneta,
That's simple and straight forward by add new property to your custom model (CustomLinkModel .cs)
and rember to update your CustomLinkItemModel.js accordingly (serialize and parse method)
Aneta Petryla - Jan 04, 2023 15:20
I've done it with ContentReference field but it was added on the top of all props and is normal field like Link Title (so optional) (It will be the best to show it only when the editor chooses the Page option). I don't know how to check to be only visible when Page radio button is selected. Probably it requires more changes in some js class but I don't know in what.

Vote:
 
I am trying to reproduce the example you propose.

but I can't figure out how it works or where the creation of step 3 and 4 is located.

How should the files be called and where are they located?

Can you give more details of this to be able to achieve the result of the example?
#288624
Oct 04, 2022 10:31
Vote:
 

Hi Daniel,

Please follow this link: Registering a custom editor (optimizely.com)

#294124
Jan 04, 2023 12:27
* You are NOT allowed to include any hyperlinks in the post because your account hasn't associated to your company. User profile should be updated.