Take the community feedback survey now.

PuneetGarg
Jan 28, 2022
  3648
(2 votes)

Custom radio control form element that displays the input box CMS 12

Episerver Forms does provide a lot of built-in functionality, but sometimes it is necessary to extend that functionality, which might give you some problems or difficulties. So in this post, I'm going to share my experience while customizing the Episerver form.

Note:- I'm doing this on CMS 12 and Episerver form 5.0.1

In this, we are going to extend the ability of the Selection element by inserting a text box with them.

1. Custom form element type

Since form elements are blocks, you create them the same way as any form of IContent. Instead of inheriting from BlockData inherit it from SelectionElementBlockBase<T>, ValidatableElementBlockBase, and many others, Right now we are going to work with the selection element so we are going to use SelectionElementBlockBase.

 public class InputBoxInChoiceElementBlock : SelectionElementBlockBase<ExtendedOptionItem>
    {
        [Display(GroupName = "Information", Order = -3000)]
        [EditorDescriptor(EditorDescriptorType = typeof(CollectionEditorDescriptor<ExtendedOptionItem>))]
        public override IEnumerable<ExtendedOptionItem> Items { get; set; }

        [Ignore]
        public override string PlaceHolder { get; set; }
        [Ignore]
        public override bool AllowMultiSelect { get; set; }

        public string GetDefaultSelectedString(ExtendedOptionItem item)
        {
            string defaultValue = this.GetDefaultValue();
            return this.GetDefaultSelectedString(item, defaultValue);
        }

        public string GetDefaultSelectedString(ExtendedOptionItem item, string defaultValue)
        {
            string str = item.Value;
            return (string.IsNullOrEmpty(str) || string.IsNullOrEmpty(defaultValue) || !((IEnumerable<string>)defaultValue.Split(',')).Contains<string>(str, (IEqualityComparer<string>)StringComparer.OrdinalIgnoreCase)) && (!item.Checked.HasValue || !item.Checked.Value || !string.IsNullOrEmpty(defaultValue)) ? string.Empty : "data-f-default-value=\"true\"";
        }
    }

2. Create a Class that inherits from IOptionItem.

This class will have all the properties of the radio button that you want to show i.e Label/Caption, Value, and others.

 public class ExtendedOptionItem : IOptionItem
    {
        [DisplayName("/episerver/forms/contentediting/optionitem/caption")]
        [Display(Order = 1000)]
        public virtual string Caption { get; set; }
        [DisplayName("/episerver/forms/contentediting/optionitem/value")]
        [Display(Order = 2000)]
        [RegularExpression("([^,])*", ErrorMessage = "/episerver/forms/contentediting/optionitem/containsinvalidcharacter")]
        public virtual string Value { get; set; }
        [DisplayName("/episerver/forms/contentediting/optionitem/checked")]
        [Display(Order = 3000)]
        public virtual bool? Checked { get; set; }
    }
    [PropertyDefinitionTypePlugIn]
    public class ExtendedOptionItemProperty : PropertyList<ExtendedOptionItem>
    {

    }

 3. Your view

You need to create your own rendering which somewhat looks like this. I didn't check for null in this code when you copy this does place your null checks.

@using (Html.BeginElement(Model, new { id = formElement.Guid, @class = "FormChoice" + cssClasses, data_f_type = "choice", aria_invalid = Util.GetAriaInvalidByValidationCssClasses(cssClasses) }, true))
{
    <fieldset aria-describedby="@Util.GetAriaDescribedByElementName(formElement.ElementName)">
       <legend class="Form__Element__Caption">@Model.Label</legend>        
            @foreach (var item in items)
            {
                var defaultCheckedString = Model.GetDefaultSelectedString(item);
                var checkedString = string.IsNullOrEmpty(defaultCheckedString) ? string.Empty : "checked";
                <label> <input type="radio" name="@formElement.ElementName" value="@item.Value" class="FormChoice__Input FormChoice__Input--Radio" @checkedString @defaultCheckedString data-f-datainput />@item.Caption</label>
            }        
        <label>
            <input type="radio" id="chk" name="@formElement.ElementName"  class="FormChoice__Input FormChoice__Input--Radio" data-f-datainput value=""/>  Other Amount ($) <input type="number" id="otherAmount" class="FormTextbox__Input wrap" data-f-datainput />
        </label>
    </fieldset>
    @Html.ValidationMessageFor(Model)
}

4. Java Script

Now we need to customize our text box like when you click on that particular radio button then only it shows and all. Do remember that by default Episerver form stores the value of the radio button, not the input box so we need to update it.

 $(document).ready(function () {
        // By Default Disable Input
        $("#otherAmount").attr('disabled', true);
        $(".wrap").css('opacity', '2');
        $("form input:radio").change(function () {
            if ($("#chk").is(":checked")) {
                $("#otherAmount").attr('disabled', false);
                $(".wrap").css('opacity', '2');
            }
            else {
                $("#otherAmount").attr('disabled', true);
                $("#otherAmount").val('');
                $(".wrap").css('opacity', '1');
            }
        });
        //Updating value of radio button
        $("#otherAmount").blur(function () {
            if ($("#chk").is(":checked")) {
                var otherAmountVal = parseInt($("#otherAmount").val());
                $("#chk").attr("value", otherAmountVal);
            }
        });
    });

That'll you need to customize the Episerver form.

Thank you

Puneet Garg

Jan 28, 2022

Comments

Please login to comment.
Latest blogs
Optimizely Opal — working notes from me

A short, practical orientation I use when introducing Opal. Lately I’ve been helping customers and developers understand Opal, and I kept finding...

Pär Wissmark | Nov 26, 2025 |

How to setup Entra ID (formerly Azure AD) for CMS 12 site

Recently, I created a doc about configuring AAD with CMS 12, but it has been posted internally only So today, I would like to introduce it again in...

Tuan Anh Hoang | Nov 25, 2025

Running Optimizely CMS 12 on .NET 10 in Azure

Upgrade your Optimizely CMS website to .NET 10!

Tomas Hensrud Gulla | Nov 21, 2025 |

Experimentation Evolution with AI (Masterclass Recap)

If you think you are not using AI in your experimentation program you are probably wrong. Ever asked an AI to rephrase a hypothesis or brainstorm a...

Polly Walton | Nov 21, 2025