Exemple #1
0
        public override Task ProcessAsync(TagHelperContext context, TagHelperOutput output)
        {
            if (!isVisible)
            {
                output.SuppressOutput();
                return(Task.CompletedTask);
            }

            ElementId = Guid.NewGuid();

            output.TagName = "div";
            output.AddCssClass($"wv-echarts {CssClass}");

            var wrapperEl = new TagBuilder("div");

            wrapperEl.Attributes.Add("id", "echarts-" + ElementId);
            wrapperEl.AddCssClass("echart");
            var style = "";

            if (!String.IsNullOrWhiteSpace(Width))
            {
                style += $"width:{Width};";
            }
            if (!String.IsNullOrWhiteSpace(Height))
            {
                style += $"height:{Height};";
            }
            wrapperEl.Attributes.Add("style", style);
            output.Content.AppendHtml(wrapperEl);

            dynamic options = null;

            if (Mode == "map")
            {
                options = new
                {
                    series = new List <dynamic> {
                        new {
                            data = new List <dynamic> {
                                new {
                                    name      = "California",
                                    value     = 1,
                                    itemStyle = new {
                                        normal = new {
                                            color = "#009688"
                                        }
                                    }
                                },
                                new {
                                    name  = "Florida",
                                    value = 0
                                }
                            },
                            type      = "map",
                            mapType   = "USA",
                            top       = 0,
                            left      = 0,
                            right     = 0,
                            markPoint = new {
                                symbol = "none"
                            },
                            zoom       = 1,
                            scaleLimit = new {
                                min = 1,
                                max = 4
                            },
                            roam      = true,
                            itemStyle = new {
                                emphasis = new {
                                    areaColor = "#ccc",
                                    color     = "#ccc",
                                    label     = new {
                                        color = "#333"
                                    }
                                }
                            }
                        }
                    }
                };
            }
            else if (Mode == "match")
            {
                options = new
                {
                    radar = new
                    {
                        indicator = new List <dynamic> {
                            new{
                                name = "profile",
                                max  = 100
                            },
                            new{
                                name = "time",
                                max  = 100
                            },
                            new{
                                name = "location",
                                max  = 100
                            },
                            new{
                                name = "experience",
                                max  = 100
                            },
                            new{
                                name = "certification",
                                max  = 100
                            },
                        }
                    },
                    series = new List <dynamic> {
                        new {
                            type  = "radar",
                            top   = 0,
                            left  = 0,
                            right = 0,
                            data  = new List <dynamic> {
                                new{
                                    areaStyle = new { color = "#009688", opacity = 0.25 },
                                    lineStyle = new { color = "#009688" },
                                    value     = new List <int> {
                                        55, 25, 5, 75, 34
                                    }
                                }
                            }
                        }
                    }
                };
            }
            else if (Mode == "expertise")
            {
                options = new
                {
                    legend = new {
                        bottom = 0,
                        top    = "auto",
                        data   = new List <dynamic> {
                            new {
                                name = "certification",
                                icon = "circle"
                            },
                            new {
                                name = "experience",
                                icon = "circle"
                            },
                            new {
                                name = "selection",
                                icon = "circle"
                            }
                        }
                    },
                    radar = new
                    {
                        indicator = new List <dynamic> {
                            new{
                                name = "Securely Provision",
                                max  = 100
                            },
                            new{
                                name = "Operate and Maintain",
                                max  = 100
                            },
                            new{
                                name = "Oversee and Govern",
                                max  = 100
                            },
                            new{
                                name = "Protect and Defend",
                                max  = 100
                            },
                            new{
                                name = "Analyze",
                                max  = 100
                            },
                            new{
                                name = "Collect and Operate",
                                max  = 100
                            },
                            new{
                                name = "Investigate",
                                max  = 100
                            },
                        }
                    },
                    series = new List <dynamic> {
                        new {
                            type  = "radar",
                            top   = 0,
                            left  = 0,
                            right = 0,
                            data  = new List <dynamic> {
                                new{
                                    areaStyle = new { color = "#009688", opacity = 0.25 },
                                    lineStyle = new { color = "#009688" },
                                    itemStyle = new { color = "#009688" },
                                    value     = new List <int> {
                                        55, 0, 0, 0, 34, 34, 0
                                    },
                                    name = "certification"
                                },
                                new{
                                    areaStyle = new { color = "#E91E63", opacity = 0.25 },
                                    lineStyle = new { color = "#E91E63" },
                                    itemStyle = new { color = "#E91E63" },
                                    value     = new List <int> {
                                        12, 33, 55, 12, 1, 33, 45
                                    },
                                    name = "experience"
                                },
                                new{
                                    areaStyle = new { color = "#2196F3", opacity = 0.25 },
                                    lineStyle = new { color = "#2196F3" },
                                    itemStyle = new { color = "#2196F3" },
                                    value     = new List <int> {
                                        85, 45, 34, 0, 0, 33, 44
                                    },
                                    name = "selection"
                                }
                            }
                        }
                    }
                };
            }
            else if (Mode == "calendar")
            {
                var calendarData = new List <dynamic>();
                for (int i = 0; i < 190; i++)
                {
                    Random r      = new Random();
                    var    number = r.Next(0, 3);
                    var    date   = DateTime.ParseExact("2019-10-01", "yyyy-MM-dd", System.Globalization.CultureInfo.InvariantCulture).AddDays(i);
                    calendarData.Add(new List <dynamic> {
                        date.ToString("yyyy-MM-dd"), number
                    });
                }

                options = new
                {
                    visualMap = new {
                        show  = false,
                        min   = 0,
                        max   = 2,
                        color = new List <string> {
                            "#E57373", "#FFB74D", "#eee"
                        }
                    },
                    calendar = new {
                        range = new List <string> {
                            "2019-10", "2020-4"
                        },
                        splitLine = new {
                            lineStyle = new {
                                color      = "#fff",
                                width      = 3,
                                shadowBlur = 0,
                                opacity    = 1
                            }
                        },
                        itemStyle = new {
                            borderColor = "#fff",
                            borderWidth = 1,
                            shadowBlur  = 0,
                            opacity     = 1
                        }
                    },
                    series = new List <dynamic> {
                        new {
                            type             = "heatmap",
                            coordinateSystem = "calendar",
                            left             = 0,
                            right            = 0,
                            data             = calendarData
                        }
                    }
                };
            }
            else if (Mode == "hits")
            {
                var calendarData   = new List <dynamic>();
                var calendaryDays  = new List <string>();
                var calendarValues = new List <int>();
                for (int i = 0; i < 190; i++)
                {
                    Random r      = new Random();
                    var    number = r.Next(0, 3);
                    var    date   = DateTime.ParseExact("2019-10-01", "yyyy-MM-dd", System.Globalization.CultureInfo.InvariantCulture).AddDays(i);
                    calendarData.Add(new List <dynamic> {
                        date.ToString("yyyy-MM-dd"), number
                    });

                    calendaryDays.Add(date.ToString("MM/dd"));
                    calendarValues.Add(r.Next(0, 300));
                }

                options = new
                {
                    visualMap = new {
                        show  = false,
                        min   = 0,
                        max   = 300,
                        color = new List <string> {
                            "#009688", "#E0F2F1"
                        }
                    },
                    xAxis = new List <dynamic> {
                        new {
                            data = calendaryDays
                        }
                    },
                    yAxis = new List <dynamic> {
                        new {
                            splitLine = new { show = false }
                        }
                    },
                    series = new List <dynamic> {
                        new {
                            type       = "line",
                            showSymbol = false,
                            data       = calendarValues
                        }
                    }
                };
            }

            var jsCompressor = new JavaScriptCompressor();

            #region << Init Echarts >>
            {
                var wvLibraryInitialized = false;
                var libraryItemsKey      = "WebVella-" + "echarts";
                if (ViewContext.HttpContext.Items.ContainsKey(libraryItemsKey))
                {
                    var tagHelperContext = (WvTagHelperContext)ViewContext.HttpContext.Items[libraryItemsKey];
                    wvLibraryInitialized = tagHelperContext.Initialized;
                }

                if (!wvLibraryInitialized)
                {
                    {
                        var libJsEl = new TagBuilder("script");
                        libJsEl.Attributes.Add("type", "text/javascript");
                        libJsEl.Attributes.Add("src", "/webvella-taghelpers/lib/echarts/echarts-en.js");
                        output.PostContent.AppendHtml(libJsEl);
                        output.PostContent.AppendHtml("\r\n\t");
                    }

                    ViewContext.HttpContext.Items[libraryItemsKey] = new WvTagHelperContext()
                    {
                        Initialized = true
                    };
                }
            }
            #endregion

            #region << Add Inline Init Script for this instance >>
            var initScript = new TagBuilder("script");
            initScript.Attributes.Add("type", "text/javascript");

            var scriptTemplate = "";
            if (Mode == "map")
            {
                scriptTemplate = @"
						$(function(){
	var myChart = echarts.init(document.getElementById(""echarts-{{ELEMENTID}}""));

	var usaJson = {{USAJSON}}

    echarts.registerMap('USA', usaJson, {
        Alaska: {              
            left: -131,
            top: 25,
            width: 15
        },
        Hawaii: {
            left: -110,        
            top: 28,
            width: 5
        },
        'Puerto Rico': {       
            left: -76,
            top: 26,
            width: 2
        }
    });

    myChart.setOption({{OPTIONS}});

myChart.on('click', function (params) {
    var stateName = params.name;
	var options = myChart.getOption();
	var stateIndex = _.findIndex(options.series[0].data,function(state){return state.name === stateName});
	if(stateIndex > -1){
		var state = options.series[0].data[stateIndex];
		if(state.value === 1){
			state.value = 0;
			delete state.itemStyle;
		}
		else{
			state.value = 1;
			state.itemStyle = {};
			state.itemStyle.normal = {};
			state.itemStyle.normal.color = '#009688';
		}
	}
	else{
		var state = {
			name: stateName,
			value: 1,
			itemStyle:{
				normal:{
					color: '#009688'
				}
			}
		}
		options.series[0].data.push(state);
	}
	myChart.setOption(options);
});

	$(window).on('resize', function(){
        if(myChart != null && myChart != undefined){
            myChart.resize();
        }
    });

	});"    ;
            }
            else if (Mode == "match" || Mode == "expertise" || Mode == "calendar" || Mode == "hits")
            {
                scriptTemplate = @"
						$(function(){
	var myChart = echarts.init(document.getElementById(""echarts-{{ELEMENTID}}""));

    myChart.setOption({{OPTIONS}});



	$(window).on('resize', function(){
        if(myChart != null && myChart != undefined){
            myChart.resize();
        }
    });

	});"    ;
            }


            var fieldConfig = new WvFieldSelectConfig()
            {
            };
            var usaJson = WvHelpers.GetEmbeddedTextResource("usa.json", "WebVella.TagHelpers.TagHelpers.WvECharts", "WebVella.TagHelpers");
            scriptTemplate = scriptTemplate.Replace("{{OPTIONS}}", JsonConvert.SerializeObject(options));
            scriptTemplate = scriptTemplate.Replace("{{USAJSON}}", usaJson);
            scriptTemplate = scriptTemplate.Replace("{{ELEMENTID}}", ElementId.ToString());

            //initScript.InnerHtml.AppendHtml(scriptTemplate);
            initScript.InnerHtml.AppendHtml(jsCompressor.Compress(scriptTemplate));

            output.PostContent.AppendHtml(initScript);
            #endregion


            return(Task.CompletedTask);
        }
        public override async Task ProcessAsync(TagHelperContext context, TagHelperOutput output)
        {
            if (!isVisible)
            {
                output.SuppressOutput();
                return;
            }
            #region << Init >>
            var initSuccess = InitField(context, output);

            if (!initSuccess)
            {
                return;
            }

            #region << Init Prepend and Append >>
            var content = await output.GetChildContentAsync();

            var htmlDoc = new HtmlDocument();
            htmlDoc.LoadHtml(content.GetContent());
            var prependTaghelper = htmlDoc.DocumentNode.Descendants("wv-field-prepend");
            var appendTagHelper  = htmlDoc.DocumentNode.Descendants("wv-field-append");

            foreach (var node in prependTaghelper)
            {
                PrependHtml.Add(node.InnerHtml.ToString());
            }

            foreach (var node in appendTagHelper)
            {
                AppendHtml.Add(node.InnerHtml.ToString());
            }

            #endregion

            #region << Validate Options >>
            if (Options == null)
            {
                var divEl = new TagBuilder("div");
                divEl.AddCssClass("form-control-plaintext erp-plain-text");

                var errorListEl = new TagBuilder("ul");
                errorListEl.AddCssClass("erp-error-list list-unstyled");

                var errorEl = new TagBuilder("li");
                errorEl.AddCssClass("go-red");

                var iconEl = new TagBuilder("span");
                iconEl.AddCssClass("fa fa-fw fa-exclamation");

                errorEl.InnerHtml.AppendHtml(iconEl);
                errorEl.InnerHtml.Append($"Error: Select options cannot be null");

                errorListEl.InnerHtml.AppendHtml(errorEl);
                divEl.InnerHtml.AppendHtml(errorListEl);
                output.Content.AppendHtml(divEl);
                //Finally
                if (SubInputEl != null)
                {
                    output.PostContent.AppendHtml(SubInputEl);
                }
                return;
            }
            #endregion

            #endregion



            #region << Render >>
            if (Mode == FieldRenderMode.Form)
            {
                if (Access == FieldAccess.Full || Access == FieldAccess.FullAndCreate)
                {
                    var inputGroupEl = new TagBuilder("div");
                    if (PrependHtml.Count > 0 || AppendHtml.Count > 0)
                    {
                        inputGroupEl.AddCssClass("input-group");
                    }
                    else
                    {
                        inputGroupEl.AddCssClass("d-flex");
                    }
                    //Prepend
                    if (PrependHtml.Count > 0)
                    {
                        var prependEl = new TagBuilder("span");
                        prependEl.AddCssClass($"input-group-prepend {(ValidationErrors.Count > 0 ? "is-invalid" : "")}");
                        foreach (var htmlString in PrependHtml)
                        {
                            prependEl.InnerHtml.AppendHtml(htmlString);
                        }
                        inputGroupEl.InnerHtml.AppendHtml(prependEl);
                    }
                    //Control
                    var selectEl = new TagBuilder("select");
                    selectEl.Attributes.Add("id", $"input-{FieldId}");
                    selectEl.Attributes.Add("name", $"{Name}");
                    var inputElCssClassList = new List <string>();
                    inputElCssClassList.Add("form-control erp-select");
                    if (ValidationErrors.Count > 0)
                    {
                        inputElCssClassList.Add("is-invalid");
                    }
                    selectEl.Attributes.Add("class", String.Join(' ', inputElCssClassList));
                    if (Required)
                    {
                        selectEl.Attributes.Add("required", null);

                        if (String.IsNullOrWhiteSpace(Value))
                        {
                            var defaultOption = Options.FirstOrDefault(x => x.Value == DefaultValue);

                            if (defaultOption != null)
                            {
                                Value = DefaultValue;
                            }
                        }
                    }
                    else
                    {
                        var optionEl = new TagBuilder("option");
                        optionEl.Attributes.Add("value", "");
                        if (String.IsNullOrWhiteSpace(Value))
                        {
                            optionEl.Attributes.Add("selected", null);
                        }
                        optionEl.InnerHtml.Append("not selected");
                        selectEl.InnerHtml.AppendHtml(optionEl);
                    }

                    foreach (var option in Options)
                    {
                        var optionEl = new TagBuilder("option");
                        optionEl.Attributes.Add("value", option.Value);
                        if (option.Value == (Value ?? "").ToString())
                        {
                            optionEl.Attributes.Add("selected", null);
                        }
                        optionEl.Attributes.Add("data-icon", option.IconClass);
                        optionEl.Attributes.Add("data-color", option.Color);
                        optionEl.InnerHtml.Append(option.Label);
                        selectEl.InnerHtml.AppendHtml(optionEl);
                    }
                    inputGroupEl.InnerHtml.AppendHtml(selectEl);
                    //Append
                    if (AppendHtml.Count > 0)
                    {
                        var appendEl = new TagBuilder("span");
                        appendEl.AddCssClass($"input-group-append {(ValidationErrors.Count > 0 ? "is-invalid" : "")}");

                        foreach (var htmlString in AppendHtml)
                        {
                            appendEl.InnerHtml.AppendHtml(htmlString);
                        }
                        inputGroupEl.InnerHtml.AppendHtml(appendEl);
                    }

                    output.Content.AppendHtml(inputGroupEl);

                    var jsCompressor = new JavaScriptCompressor();

                    #region << Init Scripts >>
                    var tagHelperInitialized = false;
                    if (ViewContext.HttpContext.Items.ContainsKey(typeof(WvFieldSelect) + "-form"))
                    {
                        var tagHelperContext = (WvTagHelperContext)ViewContext.HttpContext.Items[typeof(WvFieldSelect) + "-form"];
                        tagHelperInitialized = tagHelperContext.Initialized;
                    }
                    if (!tagHelperInitialized)
                    {
                        var scriptContent = FileService.GetEmbeddedTextResource("form.js", "WebVella.Erp.Web.TagHelpers.WvFieldSelect");
                        var scriptEl      = new TagBuilder("script");
                        scriptEl.Attributes.Add("type", "text/javascript");
                        //scriptEl.InnerHtml.AppendHtml(jsCompressor.Compress(scriptContent));
                        scriptEl.InnerHtml.AppendHtml(scriptContent);
                        output.PostContent.AppendHtml(scriptEl);

                        ViewContext.HttpContext.Items[typeof(WvFieldSelect) + "-form"] = new WvTagHelperContext()
                        {
                            Initialized = true
                        };
                    }
                    #endregion

                    #region << Add Inline Init Script for this instance >>
                    var initScript = new TagBuilder("script");
                    initScript.Attributes.Add("type", "text/javascript");
                    var scriptTemplate = @"
						$(function(){
							SelectFormInit(""{{FieldId}}"",""{{Name}}"",""{{EntityName}}"",{{ConfigJson}});
						});"                        ;
                    scriptTemplate = scriptTemplate.Replace("{{FieldId}}", (FieldId ?? null).ToString());
                    scriptTemplate = scriptTemplate.Replace("{{Name}}", Name);
                    scriptTemplate = scriptTemplate.Replace("{{EntityName}}", EntityName);
                    scriptTemplate = scriptTemplate.Replace("{{RecordId}}", (RecordId ?? null).ToString());

                    var fieldConfig = new WvFieldSelectConfig()
                    {
                        ApiUrl       = ApiUrl,
                        CanAddValues = Access == FieldAccess.FullAndCreate ? true : false,
                        IsInvalid    = ValidationErrors.Count > 0
                    };

                    scriptTemplate = scriptTemplate.Replace("{{ConfigJson}}", JsonConvert.SerializeObject(fieldConfig));

                    initScript.InnerHtml.AppendHtml(jsCompressor.Compress(scriptTemplate));

                    output.PostContent.AppendHtml(initScript);
                    #endregion


                    //TODO Implement CanAddValues
                    //@if (config.CanAddValues ?? false)
                    //{
                    //<div id="*****@*****.**" class="modal" data-backdrop="true">
                    //	<div class="modal-dialog" name="add-option">
                    //		<div class="modal-content">
                    //			<div class="modal-header">
                    //				<h5 class="modal-title">Add @(fieldMeta.Label)</h5>
                    //			</div>
                    //			<div class="modal-body">
                    //				<div class="alert alert-danger d-none"></div>
                    //				<div class="form-group">
                    //					<label class="control-label">New value</label>
                    //					<input class="form-control erp-select add-option-input" value="" required />
                    //				</div>
                    //			</div>
                    //			<div class="modal-footer">
                    //				<button class="btn btn-primary btn-sm" type="submit"><i class="fa fa-plus-circle"></i> Add</button>
                    //				<button class="btn btn-secondary btn-sm" data-dismiss="modal">Close</button>
                    //			</div>
                    //		</div>
                    //	</div>
                    //</div>

                    //}
                }
                else if (Access == FieldAccess.ReadOnly)
                {
                    var inputGroupEl = new TagBuilder("div");
                    inputGroupEl.AddCssClass("input-group");

                    //Prepend
                    if (PrependHtml.Count > 0)
                    {
                        var prependEl = new TagBuilder("span");
                        prependEl.AddCssClass($"input-group-prepend {(ValidationErrors.Count > 0 ? "is-invalid" : "")}");
                        foreach (var htmlString in PrependHtml)
                        {
                            prependEl.InnerHtml.AppendHtml(htmlString);
                        }
                        inputGroupEl.InnerHtml.AppendHtml(prependEl);
                    }
                    //Control
                    var formControlEl = new TagBuilder("div");
                    formControlEl.AddCssClass("form-control erp-select");
                    formControlEl.Attributes.Add("disabled", null);
                    formControlEl.Attributes.Add("name", Name);

                    var optionEl       = new TagBuilder("span");
                    var selectedOption = Options.FirstOrDefault(x => x.Value == (Value ?? "").ToString());
                    if (selectedOption == null)
                    {
                        optionEl.InnerHtml.Append((Value ?? "").ToString());
                        if (Value != null && (Value.ToString() != ""))
                        {
                            var optionElIcon = new TagBuilder("span");
                            optionElIcon.AddCssClass("fa fa-fw fa-exclamation-circle go-red");
                            optionElIcon.Attributes.Add("title", "the value is not supported by this field anymore");
                            optionEl.InnerHtml.AppendHtml(optionElIcon);
                        }
                    }
                    else
                    {
                        optionEl.Attributes.Add("title", selectedOption.Label);
                        optionEl.Attributes.Add("data-key", (Value ?? "").ToString());
                        if (String.IsNullOrWhiteSpace(selectedOption.IconClass))
                        {
                            optionEl.InnerHtml.Append(selectedOption.Label);
                        }
                        else
                        {
                            var color = "#999";
                            if (!String.IsNullOrWhiteSpace(selectedOption.Color))
                            {
                                color = selectedOption.Color;
                            }

                            optionEl.InnerHtml.AppendHtml($"<i class=\"{selectedOption.IconClass}\" style=\"color:{color}\"></i> {selectedOption.Label}");
                        }
                    }
                    formControlEl.InnerHtml.AppendHtml(optionEl);
                    inputGroupEl.InnerHtml.AppendHtml(formControlEl);

                    //Append
                    if (AppendHtml.Count > 0)
                    {
                        var appendEl = new TagBuilder("span");
                        appendEl.AddCssClass($"input-group-append {(ValidationErrors.Count > 0 ? "is-invalid" : "")}");

                        foreach (var htmlString in AppendHtml)
                        {
                            appendEl.InnerHtml.AppendHtml(htmlString);
                        }
                        inputGroupEl.InnerHtml.AppendHtml(appendEl);
                    }

                    output.Content.AppendHtml(inputGroupEl);
                }
            }
            else if (Mode == FieldRenderMode.Display)
            {
                if (Value != null)
                {
                    var formControlEl = new TagBuilder("div");
                    formControlEl.Attributes.Add("id", $"input-{FieldId}");
                    formControlEl.AddCssClass("form-control-plaintext erp-select");

                    var optionEl       = new TagBuilder("span");
                    var selectedOption = Options.FirstOrDefault(x => x.Value == (Value ?? "").ToString());
                    if (selectedOption == null)
                    {
                        optionEl.InnerHtml.Append((Value ?? "").ToString());
                        if (Value != null && (Value.ToString() != ""))
                        {
                            var optionElIcon = new TagBuilder("span");
                            optionElIcon.AddCssClass("fa fa-fw fa-exclamation-circle go-red");
                            optionElIcon.Attributes.Add("title", "the value is not supported by this field anymore");
                            optionEl.InnerHtml.AppendHtml(optionElIcon);
                        }
                    }
                    else
                    {
                        optionEl.Attributes.Add("title", selectedOption.Label);
                        optionEl.Attributes.Add("data-key", (Value ?? "").ToString());
                        if (String.IsNullOrWhiteSpace(selectedOption.IconClass))
                        {
                            optionEl.InnerHtml.Append(selectedOption.Label);
                        }
                        else
                        {
                            var color = "#999";
                            if (!String.IsNullOrWhiteSpace(selectedOption.Color))
                            {
                                color = selectedOption.Color;
                            }

                            optionEl.InnerHtml.AppendHtml($"<i class=\"{selectedOption.IconClass}\" style=\"color:{color}\"></i> {selectedOption.Label}");
                        }
                    }

                    formControlEl.InnerHtml.AppendHtml(optionEl);

                    output.Content.AppendHtml(formControlEl);
                }
                else
                {
                    output.Content.AppendHtml(EmptyValEl);
                }
            }
            else if (Mode == FieldRenderMode.Simple)
            {
                output.SuppressOutput();
                if (Value == null)
                {
                    output.Content.AppendHtml("");
                }
                else
                {
                    var selectedOption = Options.FirstOrDefault(x => x.Value == (Value ?? "").ToString());
                    if (selectedOption == null)
                    {
                        output.Content.Append((Value ?? "").ToString());
                        // in simple mode exclamation mark should not be rendered
                        //if (Value != null && (Value.ToString() != ""))
                        //{
                        //	var optionElIcon = new TagBuilder("span");
                        //	optionElIcon.AddCssClass("fa fa-fw fa-exclamation-circle go-red");
                        //	optionElIcon.Attributes.Add("title", "the value is not supported by this field anymore");
                        //	output.Content.AppendHtml(optionElIcon);
                        //}
                    }
                    else
                    {
                        if (String.IsNullOrWhiteSpace(selectedOption.IconClass))
                        {
                            output.Content.Append(selectedOption.Label);
                        }
                        else
                        {
                            var color = "#999";
                            if (!String.IsNullOrWhiteSpace(selectedOption.Color))
                            {
                                color = selectedOption.Color;
                            }

                            output.Content.AppendHtml($"<i class=\"{selectedOption.IconClass}\" style=\"color:{color}\"></i> {selectedOption.Label}");
                        }
                    }
                }
                return;
            }
            else if (Mode == FieldRenderMode.InlineEdit)
            {
                if (Access == FieldAccess.Full || Access == FieldAccess.FullAndCreate)
                {
                    #region << View Wrapper >>
                    {
                        var viewWrapperEl = new TagBuilder("div");
                        viewWrapperEl.AddCssClass("input-group view-wrapper");
                        viewWrapperEl.Attributes.Add("title", "double click to edit");
                        viewWrapperEl.Attributes.Add("id", $"view-{FieldId}");

                        //Prepend
                        if (PrependHtml.Count > 0)
                        {
                            var viewInputPrepend = new TagBuilder("span");
                            viewInputPrepend.AddCssClass("input-group-prepend");
                            foreach (var htmlString in PrependHtml)
                            {
                                viewInputPrepend.InnerHtml.AppendHtml(htmlString);
                            }
                            viewWrapperEl.InnerHtml.AppendHtml(viewInputPrepend);
                        }
                        //Control
                        var viewFormControlEl = new TagBuilder("div");
                        viewFormControlEl.AddCssClass("form-control erp-select");

                        var selectedOption = Options.FirstOrDefault(x => x.Value == (Value ?? "").ToString());
                        if (selectedOption == null)
                        {
                            viewFormControlEl.InnerHtml.Append((Value ?? "").ToString());
                            if (Value != null && (Value.ToString() != ""))
                            {
                                var optionElIcon = new TagBuilder("span");
                                optionElIcon.AddCssClass("fa fa-fw fa-exclamation-circle go-red");
                                optionElIcon.Attributes.Add("title", "the value is not supported by this field anymore");
                                viewFormControlEl.InnerHtml.AppendHtml(optionElIcon);
                            }
                        }
                        else
                        {
                            if (String.IsNullOrWhiteSpace(selectedOption.IconClass))
                            {
                                viewFormControlEl.InnerHtml.Append(selectedOption.Label);
                            }
                            else
                            {
                                var color = "#999";
                                if (!String.IsNullOrWhiteSpace(selectedOption.Color))
                                {
                                    color = selectedOption.Color;
                                }

                                viewFormControlEl.InnerHtml.AppendHtml($"<i class=\"{selectedOption.IconClass}\" style=\"color:{color}\"></i> {selectedOption.Label}");
                            }
                        }

                        viewWrapperEl.InnerHtml.AppendHtml(viewFormControlEl);

                        //Append
                        var viewInputActionEl = new TagBuilder("span");
                        viewInputActionEl.AddCssClass("input-group-append");
                        foreach (var htmlString in AppendHtml)
                        {
                            viewInputActionEl.InnerHtml.AppendHtml(htmlString);
                        }
                        viewInputActionEl.InnerHtml.AppendHtml("<button type=\"button\" class='btn btn-white action' title='edit'><i class='fa fa-fw fa-pencil-alt'></i></button>");
                        viewWrapperEl.InnerHtml.AppendHtml(viewInputActionEl);

                        output.Content.AppendHtml(viewWrapperEl);
                    }
                    #endregion

                    #region << Edit Wrapper>>
                    {
                        var editWrapperEl = new TagBuilder("div");
                        editWrapperEl.Attributes.Add("id", $"edit-{FieldId}");
                        editWrapperEl.Attributes.Add("style", $"display:none;");
                        editWrapperEl.AddCssClass("edit-wrapper");

                        var editInputGroupEl = new TagBuilder("div");
                        editInputGroupEl.AddCssClass("input-group");

                        //Prepend
                        if (PrependHtml.Count > 0)
                        {
                            var editInputPrepend = new TagBuilder("span");
                            editInputPrepend.AddCssClass("input-group-prepend");
                            foreach (var htmlString in PrependHtml)
                            {
                                editInputPrepend.InnerHtml.AppendHtml(htmlString);
                            }
                            editInputGroupEl.InnerHtml.AppendHtml(editInputPrepend);
                        }
                        //Control
                        var formControl         = new TagBuilder("div");
                        var inputElCssClassList = new List <string>();
                        inputElCssClassList.Add("form-control erp-select");
                        if (ValidationErrors.Count > 0)
                        {
                            inputElCssClassList.Add("is-invalid");
                        }
                        formControl.Attributes.Add("class", String.Join(' ', inputElCssClassList));

                        var selectEl = new TagBuilder("select");
                        selectEl.Attributes.Add("id", $"input-{FieldId}");
                        selectEl.Attributes.Add("name", $"{Name}");

                        if (Required)
                        {
                            selectEl.Attributes.Add("required", null);
                        }

                        selectEl.Attributes.Add("data-original-value", JsonConvert.SerializeObject((Value ?? "").ToString()));

                        foreach (var option in Options)
                        {
                            var optionEl = new TagBuilder("option");
                            optionEl.Attributes.Add("value", option.Value);
                            optionEl.Attributes.Add("data-icon", option.IconClass);
                            optionEl.Attributes.Add("data-color", option.Color);
                            if (option.Value == (Value ?? "").ToString())
                            {
                                optionEl.Attributes.Add("selected", null);
                            }
                            optionEl.InnerHtml.Append(option.Label);
                            selectEl.InnerHtml.AppendHtml(optionEl);
                        }

                        formControl.InnerHtml.AppendHtml(selectEl);
                        editInputGroupEl.InnerHtml.AppendHtml(formControl);

                        //Append
                        var editInputGroupAppendEl = new TagBuilder("span");
                        editInputGroupAppendEl.AddCssClass("input-group-append");

                        foreach (var htmlString in AppendHtml)
                        {
                            editInputGroupAppendEl.InnerHtml.AppendHtml(htmlString);
                        }
                        editInputGroupAppendEl.InnerHtml.AppendHtml("<button type=\"button\" class='btn btn-white save' title='save'><i class='fa fa-fw fa-check go-green'></i></button>");
                        editInputGroupAppendEl.InnerHtml.AppendHtml("<button type=\"button\" class='btn btn-white cancel' title='cancel'><i class='fa fa-fw fa-times go-gray'></i></button>");
                        editInputGroupEl.InnerHtml.AppendHtml(editInputGroupAppendEl);

                        editWrapperEl.InnerHtml.AppendHtml(editInputGroupEl);

                        output.Content.AppendHtml(editWrapperEl);
                    }
                    #endregion

                    var jsCompressor = new JavaScriptCompressor();
                    #region << Init Scripts >>
                    var tagHelperInitialized = false;
                    if (ViewContext.HttpContext.Items.ContainsKey(typeof(WvFieldSelect) + "-inline-edit"))
                    {
                        var tagHelperContext = (WvTagHelperContext)ViewContext.HttpContext.Items[typeof(WvFieldSelect) + "-inline-edit"];
                        tagHelperInitialized = tagHelperContext.Initialized;
                    }
                    if (!tagHelperInitialized)
                    {
                        var scriptContent = FileService.GetEmbeddedTextResource("inline-edit.js", "WebVella.Erp.Web.TagHelpers.WvFieldSelect");
                        var scriptEl      = new TagBuilder("script");
                        scriptEl.Attributes.Add("type", "text/javascript");
                        //scriptEl.InnerHtml.AppendHtml(jsCompressor.Compress(scriptContent));
                        scriptEl.InnerHtml.AppendHtml(scriptContent);
                        output.PostContent.AppendHtml(scriptEl);

                        ViewContext.HttpContext.Items[typeof(WvFieldSelect) + "-inline-edit"] = new WvTagHelperContext()
                        {
                            Initialized = true
                        };
                    }
                    #endregion

                    #region << Add Inline Init Script for this instance >>
                    var initScript = new TagBuilder("script");
                    initScript.Attributes.Add("type", "text/javascript");
                    var scriptTemplate = @"
						$(function(){
							SelectInlineEditInit(""{{FieldId}}"",""{{Name}}"",""{{EntityName}}"",""{{RecordId}}"",{{ConfigJson}});
						});"                        ;
                    scriptTemplate = scriptTemplate.Replace("{{FieldId}}", (FieldId ?? null).ToString());
                    scriptTemplate = scriptTemplate.Replace("{{Name}}", Name);
                    scriptTemplate = scriptTemplate.Replace("{{EntityName}}", EntityName);
                    scriptTemplate = scriptTemplate.Replace("{{RecordId}}", (RecordId ?? null).ToString());

                    var fieldConfig = new WvFieldSelectConfig()
                    {
                        ApiUrl       = ApiUrl,
                        CanAddValues = Access == FieldAccess.FullAndCreate ? true : false,
                        IsInvalid    = ValidationErrors.Count > 0
                    };

                    scriptTemplate = scriptTemplate.Replace("{{ConfigJson}}", JsonConvert.SerializeObject(fieldConfig));

                    initScript.InnerHtml.AppendHtml(jsCompressor.Compress(scriptTemplate));

                    output.PostContent.AppendHtml(initScript);
                    #endregion
                }
                else if (Access == FieldAccess.ReadOnly)
                {
                    var divEl = new TagBuilder("div");
                    divEl.AddCssClass("input-group");

                    //Prepend
                    if (PrependHtml.Count > 0)
                    {
                        var viewInputPrepend = new TagBuilder("span");
                        viewInputPrepend.AddCssClass("input-group-prepend");
                        foreach (var htmlString in PrependHtml)
                        {
                            viewInputPrepend.InnerHtml.AppendHtml(htmlString);
                        }
                        divEl.InnerHtml.AppendHtml(viewInputPrepend);
                    }
                    //Control
                    var formControlEl = new TagBuilder("div");
                    formControlEl.AddCssClass("form-control erp-select");

                    var optionEl = new TagBuilder("span");
                    optionEl.Attributes.Add("selected", null);
                    var selectedOption = Options.FirstOrDefault(x => x.Value == (Value ?? "").ToString());
                    if (selectedOption == null)
                    {
                        optionEl.InnerHtml.Append((Value ?? "").ToString());
                        if (Value != null && (Value.ToString() != ""))
                        {
                            var optionElIcon = new TagBuilder("span");
                            optionElIcon.AddCssClass("fa fa-fw fa-exclamation-circle go-red");
                            optionElIcon.Attributes.Add("title", "the value is not supported by this field anymore");
                            optionEl.InnerHtml.AppendHtml(optionElIcon);
                        }
                    }
                    else
                    {
                        optionEl.Attributes.Add("title", selectedOption.Label);
                        optionEl.Attributes.Add("data-key", (Value ?? "").ToString());
                        if (String.IsNullOrWhiteSpace(selectedOption.IconClass))
                        {
                            optionEl.InnerHtml.Append(selectedOption.Label);
                        }
                        else
                        {
                            var color = "#999";
                            if (!String.IsNullOrWhiteSpace(selectedOption.Color))
                            {
                                color = selectedOption.Color;
                            }

                            optionEl.InnerHtml.AppendHtml($"<i class=\"{selectedOption.IconClass}\" style=\"color:{color}\"></i> {selectedOption.Label}");
                        }
                    }
                    formControlEl.InnerHtml.AppendHtml(optionEl);

                    divEl.InnerHtml.AppendHtml(formControlEl);
                    //Append
                    var appendActionSpan = new TagBuilder("span");
                    appendActionSpan.AddCssClass("input-group-append");
                    foreach (var htmlString in AppendHtml)
                    {
                        appendActionSpan.InnerHtml.AppendHtml(htmlString);
                    }
                    appendActionSpan.InnerHtml.AppendHtml("<button type=\"button\" disabled class='btn btn-white action' title='locked'><i class='fa fa-fw fa-lock'></i></button>");
                    divEl.InnerHtml.AppendHtml(appendActionSpan);

                    output.Content.AppendHtml(divEl);
                }
            }
            #endregion


            //Finally
            if (SubInputEl != null)
            {
                output.PostContent.AppendHtml(SubInputEl);
            }

            return;
        }
Exemple #3
0
        public override async Task ProcessAsync(TagHelperContext context, TagHelperOutput output)
        {
            if (!isVisible)
            {
                output.SuppressOutput();
                return;
            }

            #region << Init >>
            var initSuccess = InitField(context, output);

            if (!initSuccess)
            {
                return;
            }

            #endregion



            #region << Render >>
            if (Mode == WvFieldRenderMode.Form)
            {
                if (Access == WvFieldAccess.Full || Access == WvFieldAccess.FullAndCreate)
                {
                    var inputGroupEl = new TagBuilder("div");
                    inputGroupEl.AddCssClass("input-group");

                    var prependIcon = new TagBuilder("div");
                    prependIcon.AddCssClass("input-group-prepend");
                    prependIcon.InnerHtml.AppendHtml($"<span class=\"input-group-text\"><i class=\"fa-fw {(Value != null ? Value.ToString() : "")}\"></i></span>");
                    inputGroupEl.InnerHtml.AppendHtml(prependIcon);


                    //Control
                    var selectEl = new TagBuilder("select");
                    selectEl.Attributes.Add("id", $"input-{FieldId}");
                    selectEl.Attributes.Add("name", $"{Name}");
                    var inputElCssClassList = new List <string>();
                    inputElCssClassList.Add("form-control erp-select");
                    if (ValidationErrors.Count > 0)
                    {
                        inputElCssClassList.Add("is-invalid");
                    }
                    selectEl.Attributes.Add("class", String.Join(' ', inputElCssClassList));
                    if (Required)
                    {
                        selectEl.Attributes.Add("required", null);
                    }
                    else
                    {
                        var optionEl = new TagBuilder("option");
                        selectEl.InnerHtml.AppendHtml(optionEl);
                    }

                    if (!String.IsNullOrWhiteSpace((string)Value))
                    {
                        var optionEl = new TagBuilder("option");
                        optionEl.Attributes.Add("value", Value.ToString());
                        optionEl.Attributes.Add("selected", null);
                        optionEl.InnerHtml.Append(Value.ToString());
                        selectEl.InnerHtml.AppendHtml(optionEl);
                    }

                    inputGroupEl.InnerHtml.AppendHtml(selectEl);

                    output.Content.AppendHtml(inputGroupEl);

                    var jsCompressor = new JavaScriptCompressor();

                    #region << Init FA Icons >>
                    {
                        var wvFAIconsLibraryInitialized = false;
                        var libraryItemsKey             = "WebVella-" + "fontawesome-icon-json";
                        if (ViewContext.HttpContext.Items.ContainsKey(libraryItemsKey))
                        {
                            var tagHelperContext = (WvTagHelperContext)ViewContext.HttpContext.Items[libraryItemsKey];
                            wvFAIconsLibraryInitialized = tagHelperContext.Initialized;
                        }

                        if (!wvFAIconsLibraryInitialized)
                        {
                            var libJsEl = new TagBuilder("script");
                            libJsEl.Attributes.Add("type", "text/javascript");
                            var scriptIconTemplate = @"
								WvFontAwesomeIcons = {{FAIcons}}
							"                            ;
                            scriptIconTemplate = scriptIconTemplate.Replace("{{FAIcons}}", JsonConvert.SerializeObject(WvHelpers.GetAllFontAwesomeIcons()));
                            libJsEl.InnerHtml.AppendHtml(jsCompressor.Compress(scriptIconTemplate));

                            output.PostContent.AppendHtml(libJsEl);
                            output.PostContent.AppendHtml("\r\n\t");

                            ViewContext.HttpContext.Items[libraryItemsKey] = new WvTagHelperContext()
                            {
                                Initialized = true
                            };
                        }
                    }
                    #endregion

                    #region << Init Select2 >>
                    {
                        var wvLibraryInitialized = false;
                        var libraryItemsKey      = "WebVella-" + "select2";
                        if (ViewContext.HttpContext.Items.ContainsKey(libraryItemsKey))
                        {
                            var tagHelperContext = (WvTagHelperContext)ViewContext.HttpContext.Items[libraryItemsKey];
                            wvLibraryInitialized = tagHelperContext.Initialized;
                        }

                        if (!wvLibraryInitialized)
                        {
                            {
                                var libCssEl = new TagBuilder("link");
                                libCssEl.Attributes.Add("href", "/_content/WebVella.TagHelpers/lib/select2/css/select2.min.css");
                                libCssEl.Attributes.Add("type", "text/css");
                                libCssEl.Attributes.Add("rel", "stylesheet");
                                output.PostContent.AppendHtml(libCssEl);
                                output.PostContent.AppendHtml("\r\n\t");
                            }
                            {
                                var libCssEl = new TagBuilder("link");
                                libCssEl.Attributes.Add("href", "/_content/WebVella.TagHelpers/lib/select2-bootstrap-theme/select2-bootstrap4.css");
                                libCssEl.Attributes.Add("type", "text/css");
                                libCssEl.Attributes.Add("rel", "stylesheet");
                                output.PostContent.AppendHtml(libCssEl);
                                output.PostContent.AppendHtml("\r\n\t");
                            }

                            var libJsEl = new TagBuilder("script");
                            libJsEl.Attributes.Add("type", "text/javascript");
                            libJsEl.Attributes.Add("src", "/_content/WebVella.TagHelpers/lib/select2/js/select2.min.js");
                            output.PostContent.AppendHtml(libJsEl);
                            output.PostContent.AppendHtml("\r\n\t");

                            ViewContext.HttpContext.Items[libraryItemsKey] = new WvTagHelperContext()
                            {
                                Initialized = true
                            };
                        }
                    }
                    #endregion

                    #region << Init Scripts >>
                    var tagHelperInitialized = false;
                    if (ViewContext.HttpContext.Items.ContainsKey(typeof(WvFieldIcon) + "-form"))
                    {
                        var tagHelperContext = (WvTagHelperContext)ViewContext.HttpContext.Items[typeof(WvFieldIcon) + "-form"];
                        tagHelperInitialized = tagHelperContext.Initialized;
                    }
                    if (!tagHelperInitialized)
                    {
                        var scriptContent = WvHelpers.GetEmbeddedTextResource("form.js", "WebVella.TagHelpers.TagHelpers.WvFieldIcon", "WebVella.TagHelpers");
                        var scriptEl      = new TagBuilder("script");
                        scriptEl.Attributes.Add("type", "text/javascript");
                        //scriptEl.InnerHtml.AppendHtml(jsCompressor.Compress(scriptContent));
                        scriptEl.InnerHtml.AppendHtml(scriptContent);
                        output.PostContent.AppendHtml(scriptEl);

                        ViewContext.HttpContext.Items[typeof(WvFieldIcon) + "-form"] = new WvTagHelperContext()
                        {
                            Initialized = true
                        };
                    }
                    #endregion

                    #region << Add Inline Init Script for this instance >>
                    var initScript = new TagBuilder("script");
                    initScript.Attributes.Add("type", "text/javascript");
                    var scriptTemplate = @"
						$(function(){
							IconFieldFormInit(""{{FieldId}}"",""{{Name}}"",{{ConfigJson}});
						});"                        ;
                    scriptTemplate = scriptTemplate.Replace("{{FieldId}}", (FieldId != null ? FieldId.Value.ToString() : ""));
                    scriptTemplate = scriptTemplate.Replace("{{Name}}", Name);

                    var fieldConfig = new WvFieldSelectConfig()
                    {
                        ApiUrl       = ApiUrl,
                        CanAddValues = Access == WvFieldAccess.FullAndCreate ? true : false,
                        IsInvalid    = ValidationErrors.Count > 0
                    };

                    scriptTemplate = scriptTemplate.Replace("{{ConfigJson}}", JsonConvert.SerializeObject(fieldConfig));

                    initScript.InnerHtml.AppendHtml(jsCompressor.Compress(scriptTemplate));

                    output.PostContent.AppendHtml(initScript);
                    #endregion
                }
                else if (Access == WvFieldAccess.ReadOnly)
                {
                    //Have to render it as a normal select as readonly prop does not work with select 2. Also in order for the select not to work it should be disabled,
                    //which will not pass the value, this the hidden input

                    //Hidden input
                    var hiddenEl = new TagBuilder("input");
                    hiddenEl.Attributes.Add("id", $"input-{FieldId}");
                    hiddenEl.Attributes.Add("name", $"{Name}");
                    hiddenEl.Attributes.Add("value", (Value ?? "").ToString());
                    hiddenEl.Attributes.Add("type", "hidden");
                    output.Content.AppendHtml(hiddenEl);

                    var inputGroupEl = new TagBuilder("div");
                    inputGroupEl.AddCssClass("input-group");

                    var prependIcon = new TagBuilder("div");
                    prependIcon.AddCssClass("input-group-prepend");
                    prependIcon.InnerHtml.AppendHtml($"<span class=\"input-group-text\"><i class=\"fa-fw {(Value != null ? Value.ToString() : "")}\"></i></span>");
                    inputGroupEl.InnerHtml.AppendHtml(prependIcon);

                    //Dummy disabled select
                    var selectEl = new TagBuilder("select");
                    selectEl.Attributes.Add("id", $"select-{FieldId}");
                    selectEl.Attributes.Add("readonly", null);
                    selectEl.Attributes.Add("disabled", "disabled");
                    var inputElCssClassList = new List <string>();
                    inputElCssClassList.Add("form-control erp-select");
                    if (ValidationErrors.Count > 0)
                    {
                        inputElCssClassList.Add("is-invalid");
                    }
                    selectEl.Attributes.Add("class", String.Join(' ', inputElCssClassList));
                    if (Required)
                    {
                        selectEl.Attributes.Add("required", null);
                    }
                    if (Value != null)
                    {
                        var optionEl = new TagBuilder("option");
                        optionEl.Attributes.Add("value", Value.ToString());
                        optionEl.Attributes.Add("selected", null);
                        optionEl.InnerHtml.Append(Value.ToString());
                        selectEl.InnerHtml.AppendHtml(optionEl);
                    }

                    inputGroupEl.InnerHtml.AppendHtml(selectEl);

                    output.Content.AppendHtml(inputGroupEl);
                }
            }
            else if (Mode == WvFieldRenderMode.Display)
            {
                if (Value != null)
                {
                    var formControlEl = new TagBuilder("div");
                    formControlEl.Attributes.Add("id", $"input-{FieldId}");
                    formControlEl.AddCssClass("form-control-plaintext erp-select");

                    var optionEl = new TagBuilder("span");
                    optionEl.Attributes.Add("data-key", (Value ?? "").ToString());
                    var color = "#333";
                    optionEl.InnerHtml.AppendHtml($"<i class=\"fa-fw {Value.ToString()}\" style=\"color:{color}\"></i> {Value.ToString()}");

                    formControlEl.InnerHtml.AppendHtml(optionEl);

                    output.Content.AppendHtml(formControlEl);
                }
                else
                {
                    output.Content.AppendHtml(EmptyValEl);
                }
            }
            else if (Mode == WvFieldRenderMode.Simple)
            {
                output.SuppressOutput();
                if (Value == null)
                {
                    output.Content.AppendHtml("");
                }
                else
                {
                    var color = "#333";
                    output.Content.AppendHtml($"<i class=\"fa-fw {Value.ToString()}\" style=\"color:{color}\"></i> {Value.ToString()}");
                }
                return;
            }
            else if (Mode == WvFieldRenderMode.InlineEdit)
            {
                if (Access == WvFieldAccess.Full || Access == WvFieldAccess.FullAndCreate)
                {
                    #region << View Wrapper >>
                    {
                        var viewWrapperEl = new TagBuilder("div");
                        viewWrapperEl.AddCssClass("input-group view-wrapper");
                        viewWrapperEl.Attributes.Add("title", "double click to edit");
                        viewWrapperEl.Attributes.Add("id", $"view-{FieldId}");

                        var prependIcon = new TagBuilder("div");
                        prependIcon.AddCssClass("input-group-prepend");
                        prependIcon.InnerHtml.AppendHtml($"<span class=\"input-group-text\"><i class=\"fa-fw {(Value != null ? Value.ToString() : "")}\"></i></span>");
                        viewWrapperEl.InnerHtml.AppendHtml(prependIcon);

                        //Control
                        var viewFormControlEl = new TagBuilder("div");
                        viewFormControlEl.AddCssClass("form-control erp-select");

                        if (Value != null)
                        {
                            viewFormControlEl.InnerHtml.AppendHtml($"{Value.ToString()}");
                        }

                        viewWrapperEl.InnerHtml.AppendHtml(viewFormControlEl);

                        //Append
                        var viewInputActionEl = new TagBuilder("span");
                        viewInputActionEl.AddCssClass("input-group-append action");
                        viewInputActionEl.InnerHtml.AppendHtml("<button type=\"button\" class='btn btn-white ' title='edit'><i class='fa fa-fw fa-pencil-alt'></i></button>");
                        viewWrapperEl.InnerHtml.AppendHtml(viewInputActionEl);

                        output.Content.AppendHtml(viewWrapperEl);
                    }
                    #endregion

                    #region << Edit Wrapper>>
                    {
                        var editWrapperEl = new TagBuilder("div");
                        editWrapperEl.Attributes.Add("id", $"edit-{FieldId}");
                        editWrapperEl.Attributes.Add("style", $"display:none;");
                        editWrapperEl.AddCssClass("edit-wrapper");

                        var editInputGroupEl = new TagBuilder("div");
                        editInputGroupEl.AddCssClass("input-group");

                        var prependIcon = new TagBuilder("div");
                        prependIcon.AddCssClass("input-group-prepend");
                        prependIcon.InnerHtml.AppendHtml($"<span class=\"input-group-text\"><i class=\"fa-fw {(Value != null ? Value.ToString() : "")}\"></i></span>");
                        editInputGroupEl.InnerHtml.AppendHtml(prependIcon);


                        //Control
                        var formControl         = new TagBuilder("select");
                        var inputElCssClassList = new List <string>();
                        inputElCssClassList.Add("form-control erp-select");
                        if (ValidationErrors.Count > 0)
                        {
                            inputElCssClassList.Add("is-invalid");
                        }
                        formControl.Attributes.Add("class", String.Join(' ', inputElCssClassList));
                        formControl.Attributes.Add("id", $"input-{FieldId}");

                        if (Required)
                        {
                            formControl.Attributes.Add("required", null);
                        }

                        formControl.Attributes.Add("data-original-value", JsonConvert.SerializeObject((Value ?? "").ToString()));

                        if (Value != null)
                        {
                            var optionEl = new TagBuilder("option");
                            optionEl.Attributes.Add("value", Value.ToString());
                            optionEl.Attributes.Add("selected", null);
                            optionEl.InnerHtml.Append(Value.ToString());
                            formControl.InnerHtml.AppendHtml(optionEl);
                        }

                        editInputGroupEl.InnerHtml.AppendHtml(formControl);

                        //Append
                        var editInputGroupAppendEl = new TagBuilder("span");
                        editInputGroupAppendEl.AddCssClass("input-group-append");

                        foreach (var htmlString in AppendHtml)
                        {
                            editInputGroupAppendEl.InnerHtml.AppendHtml(htmlString);
                        }
                        editInputGroupAppendEl.InnerHtml.AppendHtml("<button type=\"button\" class='btn btn-white save' title='save'><i class='fa fa-fw fa-check go-green'></i></button>");
                        editInputGroupAppendEl.InnerHtml.AppendHtml("<button type=\"button\" class='btn btn-white cancel' title='cancel'><i class='fa fa-fw fa-times go-gray'></i></button>");
                        editInputGroupEl.InnerHtml.AppendHtml(editInputGroupAppendEl);

                        editWrapperEl.InnerHtml.AppendHtml(editInputGroupEl);

                        output.Content.AppendHtml(editWrapperEl);
                    }
                    #endregion

                    var jsCompressor = new JavaScriptCompressor();

                    #region << Init Libraries >>
                    {
                        var wvLibraryInitialized = false;
                        var libraryItemsKey      = "WebVella-" + "fontawesome-icon-json";
                        if (ViewContext.HttpContext.Items.ContainsKey(libraryItemsKey))
                        {
                            var tagHelperContext = (WvTagHelperContext)ViewContext.HttpContext.Items[libraryItemsKey];
                            wvLibraryInitialized = tagHelperContext.Initialized;
                        }

                        if (!wvLibraryInitialized)
                        {
                            var libJsEl = new TagBuilder("script");
                            libJsEl.Attributes.Add("type", "text/javascript");
                            var scriptIconTemplate = @"
								var WvFontAwesomeIcons = {{FAIcons}}
							"                            ;
                            scriptIconTemplate = scriptIconTemplate.Replace("{{FAIcons}}", JsonConvert.SerializeObject(WvHelpers.GetAllFontAwesomeIcons()));
                            libJsEl.InnerHtml.AppendHtml(jsCompressor.Compress(scriptIconTemplate));

                            output.PostContent.AppendHtml(libJsEl);
                            output.PostContent.AppendHtml("\r\n\t");

                            ViewContext.HttpContext.Items[libraryItemsKey] = new WvTagHelperContext()
                            {
                                Initialized = true
                            };
                        }
                    }
                    #endregion

                    #region << Init Select2 >>
                    {
                        var wvLibraryInitialized = false;
                        var libraryItemsKey      = "WebVella-" + "select2";
                        if (ViewContext.HttpContext.Items.ContainsKey(libraryItemsKey))
                        {
                            var tagHelperContext = (WvTagHelperContext)ViewContext.HttpContext.Items[libraryItemsKey];
                            wvLibraryInitialized = tagHelperContext.Initialized;
                        }

                        if (!wvLibraryInitialized)
                        {
                            {
                                var libCssEl = new TagBuilder("link");
                                libCssEl.Attributes.Add("href", "/_content/WebVella.TagHelpers/lib/select2/css/select2.min.css");
                                libCssEl.Attributes.Add("type", "text/css");
                                libCssEl.Attributes.Add("rel", "stylesheet");
                                output.PostContent.AppendHtml(libCssEl);
                                output.PostContent.AppendHtml("\r\n\t");
                            }
                            {
                                var libCssEl = new TagBuilder("link");
                                libCssEl.Attributes.Add("href", "/_content/WebVella.TagHelpers/lib/select2-bootstrap-theme/select2-bootstrap4.css");
                                libCssEl.Attributes.Add("type", "text/css");
                                libCssEl.Attributes.Add("rel", "stylesheet");
                                output.PostContent.AppendHtml(libCssEl);
                                output.PostContent.AppendHtml("\r\n\t");
                            }
                            var libJsEl = new TagBuilder("script");
                            libJsEl.Attributes.Add("type", "text/javascript");
                            libJsEl.Attributes.Add("src", "/_content/WebVella.TagHelpers/lib/select2/js/select2.min.js");
                            output.PostContent.AppendHtml(libJsEl);
                            output.PostContent.AppendHtml("\r\n\t");

                            ViewContext.HttpContext.Items[libraryItemsKey] = new WvTagHelperContext()
                            {
                                Initialized = true
                            };
                        }
                    }
                    #endregion

                    #region << Init Scripts >>
                    var tagHelperInitialized = false;
                    if (ViewContext.HttpContext.Items.ContainsKey(typeof(WvFieldIcon) + "-inline-edit"))
                    {
                        var tagHelperContext = (WvTagHelperContext)ViewContext.HttpContext.Items[typeof(WvFieldIcon) + "-inline-edit"];
                        tagHelperInitialized = tagHelperContext.Initialized;
                    }
                    if (!tagHelperInitialized)
                    {
                        var scriptContent = WvHelpers.GetEmbeddedTextResource("inline-edit.js", "WebVella.TagHelpers.TagHelpers.WvFieldIcon", "WebVella.TagHelpers");
                        var scriptEl      = new TagBuilder("script");
                        scriptEl.Attributes.Add("type", "text/javascript");
                        //scriptEl.InnerHtml.AppendHtml(jsCompressor.Compress(scriptContent));
                        scriptEl.InnerHtml.AppendHtml(scriptContent);
                        output.PostContent.AppendHtml(scriptEl);

                        ViewContext.HttpContext.Items[typeof(WvFieldIcon) + "-inline-edit"] = new WvTagHelperContext()
                        {
                            Initialized = true
                        };
                    }
                    #endregion

                    #region << Add Inline Init Script for this instance >>
                    var initScript = new TagBuilder("script");
                    initScript.Attributes.Add("type", "text/javascript");
                    var scriptTemplate = @"
						$(function(){
							IconFieldInlineEditInit(""{{FieldId}}"",""{{Name}}"",{{ConfigJson}});
						});"                        ;
                    scriptTemplate = scriptTemplate.Replace("{{FieldId}}", (FieldId != null ? FieldId.Value.ToString() : ""));
                    scriptTemplate = scriptTemplate.Replace("{{Name}}", Name);

                    var fieldConfig = new WvFieldSelectConfig()
                    {
                        ApiUrl       = ApiUrl,
                        CanAddValues = Access == WvFieldAccess.FullAndCreate ? true : false,
                        IsInvalid    = ValidationErrors.Count > 0
                    };

                    scriptTemplate = scriptTemplate.Replace("{{ConfigJson}}", JsonConvert.SerializeObject(fieldConfig));

                    initScript.InnerHtml.AppendHtml(jsCompressor.Compress(scriptTemplate));

                    output.PostContent.AppendHtml(initScript);
                    #endregion
                }
                else if (Access == WvFieldAccess.ReadOnly)
                {
                    var divEl = new TagBuilder("div");
                    divEl.AddCssClass("input-group");

                    var prependIcon = new TagBuilder("div");
                    prependIcon.AddCssClass("input-group-prepend");
                    prependIcon.InnerHtml.AppendHtml($"<span class=\"input-group-text\"><i class=\"fa-fw {(Value != null ? Value.ToString() : "")}\"></i></span>");
                    divEl.InnerHtml.AppendHtml(prependIcon);

                    //Control
                    var formControlEl = new TagBuilder("div");
                    formControlEl.AddCssClass("form-control erp-select");


                    if (Value != null)
                    {
                        var optionEl = new TagBuilder("option");
                        optionEl.Attributes.Add("value", Value.ToString());
                        optionEl.Attributes.Add("selected", null);
                        optionEl.InnerHtml.Append(Value.ToString());
                        formControlEl.InnerHtml.AppendHtml(optionEl);
                    }

                    divEl.InnerHtml.AppendHtml(formControlEl);
                    //Append
                    var appendActionSpan = new TagBuilder("span");
                    appendActionSpan.AddCssClass("input-group-append");
                    foreach (var htmlString in AppendHtml)
                    {
                        appendActionSpan.InnerHtml.AppendHtml(htmlString);
                    }
                    appendActionSpan.InnerHtml.AppendHtml("<button type=\"button\" disabled class='btn btn-white' title='locked'><i class='fa fa-fw fa-lock'></i></button>");
                    divEl.InnerHtml.AppendHtml(appendActionSpan);

                    output.Content.AppendHtml(divEl);
                }
            }
            #endregion


            //Finally
            if (SubInputEl != null)
            {
                output.PostContent.AppendHtml(SubInputEl);
            }

            return;
        }
Exemple #4
0
        public override async Task ProcessAsync(TagHelperContext context, TagHelperOutput output)
        {
            if (!isVisible)
            {
                output.SuppressOutput();
                return;
            }

            #region << Init >>
            var initSuccess = InitField(context, output);

            if (!initSuccess)
            {
                return;
            }

            if (Options == null)
            {
                Options = new List <WvSelectOption>();
            }

            if (Options.Count == 0 && AjaxDatasource != null && AjaxDatasource.InitOptions.Count > 0)
            {
                Options = AjaxDatasource.InitOptions;
            }

            if (AjaxDatasource != null && String.IsNullOrWhiteSpace(AjaxDatasourceApi))
            {
                if (!AjaxDatasource.UseSelectApi)
                {
                    //old fashion call
                    AjaxDatasourceApi = "/api/v3/en_US/eql-ds";
                }
                else
                {
                    //The new api
                    AjaxDatasourceApi = "/api/v3/en_US/eql-ds-select2";
                }
            }


            #region << Init Prepend and Append >>
            var content = await output.GetChildContentAsync();

            var htmlDoc = new HtmlDocument();
            htmlDoc.LoadHtml(content.GetContent());
            var prependTaghelper = htmlDoc.DocumentNode.Descendants("wv-field-prepend");
            var appendTagHelper  = htmlDoc.DocumentNode.Descendants("wv-field-append");

            foreach (var node in prependTaghelper)
            {
                PrependHtml.Add(node.InnerHtml.ToString());
            }

            foreach (var node in appendTagHelper)
            {
                AppendHtml.Add(node.InnerHtml.ToString());
            }

            #endregion

            #region << Validate Options >>
            if (Options == null)
            {
                var divEl = new TagBuilder("div");
                divEl.AddCssClass("form-control-plaintext erp-plain-text");

                var errorListEl = new TagBuilder("ul");
                errorListEl.AddCssClass("erp-error-list list-unstyled");

                var errorEl = new TagBuilder("li");
                errorEl.AddCssClass("go-red");

                var iconEl = new TagBuilder("span");
                iconEl.AddCssClass("fa fa-fw fa-exclamation");

                errorEl.InnerHtml.AppendHtml(iconEl);
                errorEl.InnerHtml.Append($"Error: Select options cannot be null");

                errorListEl.InnerHtml.AppendHtml(errorEl);
                divEl.InnerHtml.AppendHtml(errorListEl);
                output.Content.AppendHtml(divEl);
                //Finally
                if (SubInputEl != null)
                {
                    output.PostContent.AppendHtml(SubInputEl);
                }
                return;
            }
            #endregion

            #endregion



            #region << Render >>
            if (Mode == WvFieldRenderMode.Form)
            {
                if (Access == WvFieldAccess.Full || Access == WvFieldAccess.FullAndCreate)
                {
                    var inputGroupEl = new TagBuilder("div");
                    if (PrependHtml.Count > 0 || AppendHtml.Count > 0)
                    {
                        inputGroupEl.AddCssClass("input-group");
                    }
                    else
                    {
                        inputGroupEl.AddCssClass("");
                    }
                    //Prepend
                    if (PrependHtml.Count > 0)
                    {
                        var prependEl = new TagBuilder("span");
                        prependEl.AddCssClass($"input-group-prepend {(ValidationErrors.Count > 0 ? "is-invalid" : "")}");
                        foreach (var htmlString in PrependHtml)
                        {
                            prependEl.InnerHtml.AppendHtml(htmlString);
                        }
                        inputGroupEl.InnerHtml.AppendHtml(prependEl);
                    }
                    //Control
                    var selectEl = new TagBuilder("select");
                    selectEl.Attributes.Add("id", $"input-{FieldId}");
                    selectEl.Attributes.Add("name", $"{Name}");
                    var inputElCssClassList = new List <string>();
                    inputElCssClassList.Add("form-control erp-select");
                    if (ValidationErrors.Count > 0)
                    {
                        inputElCssClassList.Add("is-invalid");
                    }
                    selectEl.Attributes.Add("class", String.Join(' ', inputElCssClassList));
                    var emptyOptionAdded = false;
                    if (Required)
                    {
                        selectEl.Attributes.Add("required", null);

                        if (String.IsNullOrWhiteSpace(Value))
                        {
                            var defaultOption = Options.FirstOrDefault(x => x.Value == DefaultValue);

                            if (defaultOption != null)
                            {
                                Value = DefaultValue;
                            }
                        }
                    }
                    else
                    {
                        var optionEl = new TagBuilder("option");
                        // Should work only with <option></option> and the select2 placeholder to be presented
                        selectEl.InnerHtml.AppendHtml(optionEl);
                        emptyOptionAdded = true;
                    }

                    foreach (var option in Options)
                    {
                        var optionEl = new TagBuilder("option");
                        optionEl.Attributes.Add("value", option.Value);
                        if (option.Value == (Value ?? "").ToString())
                        {
                            optionEl.Attributes.Add("selected", null);
                        }
                        optionEl.Attributes.Add("data-icon", option.IconClass);
                        optionEl.Attributes.Add("data-color", option.Color);
                        optionEl.InnerHtml.Append(option.Label);
                        selectEl.InnerHtml.AppendHtml(optionEl);
                    }

                    //At least one option should be in the select so it can submit
                    if (!emptyOptionAdded && Options.Count == 0)
                    {
                        var optionEl = new TagBuilder("option");
                        // Should work only with <option></option> and the select2 placeholder to be presented
                        selectEl.InnerHtml.AppendHtml(optionEl);
                    }

                    inputGroupEl.InnerHtml.AppendHtml(selectEl);
                    //Append
                    if (AppendHtml.Count > 0)
                    {
                        var appendEl = new TagBuilder("span");
                        appendEl.AddCssClass($"input-group-append {(ValidationErrors.Count > 0 ? "is-invalid" : "")}");

                        foreach (var htmlString in AppendHtml)
                        {
                            appendEl.InnerHtml.AppendHtml(htmlString);
                        }
                        inputGroupEl.InnerHtml.AppendHtml(appendEl);
                    }

                    output.Content.AppendHtml(inputGroupEl);

                    var jsCompressor = new JavaScriptCompressor();

                    #region << Init Select2 >>
                    {
                        var wvLibraryInitialized = false;
                        var libraryItemsKey      = "WebVella-" + "select2";
                        if (ViewContext.HttpContext.Items.ContainsKey(libraryItemsKey))
                        {
                            var tagHelperContext = (WvTagHelperContext)ViewContext.HttpContext.Items[libraryItemsKey];
                            wvLibraryInitialized = tagHelperContext.Initialized;
                        }

                        if (!wvLibraryInitialized)
                        {
                            {
                                var libCssEl = new TagBuilder("link");
                                libCssEl.Attributes.Add("href", "/_content/WebVella.TagHelpers/lib/select2/css/select2.min.css");
                                libCssEl.Attributes.Add("type", "text/css");
                                libCssEl.Attributes.Add("rel", "stylesheet");
                                output.PostContent.AppendHtml(libCssEl);
                                output.PostContent.AppendHtml("\r\n\t");
                            }
                            {
                                var libCssEl = new TagBuilder("link");
                                libCssEl.Attributes.Add("href", "/_content/WebVella.TagHelpers/lib/select2-bootstrap-theme/select2-bootstrap4.css");
                                libCssEl.Attributes.Add("type", "text/css");
                                libCssEl.Attributes.Add("rel", "stylesheet");
                                output.PostContent.AppendHtml(libCssEl);
                                output.PostContent.AppendHtml("\r\n\t");
                            }

                            var libJsEl = new TagBuilder("script");
                            libJsEl.Attributes.Add("type", "text/javascript");
                            libJsEl.Attributes.Add("src", "/_content/WebVella.TagHelpers/lib/select2/js/select2.min.js");
                            output.PostContent.AppendHtml(libJsEl);
                            output.PostContent.AppendHtml("\r\n\t");

                            ViewContext.HttpContext.Items[libraryItemsKey] = new WvTagHelperContext()
                            {
                                Initialized = true
                            };
                        }
                    }
                    #endregion


                    #region << Init Scripts >>
                    var tagHelperInitialized = false;
                    if (ViewContext.HttpContext.Items.ContainsKey(typeof(WvFieldSelect) + "-form"))
                    {
                        var tagHelperContext = (WvTagHelperContext)ViewContext.HttpContext.Items[typeof(WvFieldSelect) + "-form"];
                        tagHelperInitialized = tagHelperContext.Initialized;
                    }
                    if (!tagHelperInitialized)
                    {
                        var scriptContent = WvHelpers.GetEmbeddedTextResource("form.js", "WebVella.TagHelpers.TagHelpers.WvFieldSelect", "WebVella.TagHelpers");
                        var scriptEl      = new TagBuilder("script");
                        scriptEl.Attributes.Add("type", "text/javascript");
                        //scriptEl.InnerHtml.AppendHtml(jsCompressor.Compress(scriptContent));
                        scriptEl.InnerHtml.AppendHtml(scriptContent);
                        output.PostContent.AppendHtml(scriptEl);

                        ViewContext.HttpContext.Items[typeof(WvFieldSelect) + "-form"] = new WvTagHelperContext()
                        {
                            Initialized = true
                        };
                    }
                    #endregion

                    #region << Add Inline Init Script for this instance >>
                    var initScript = new TagBuilder("script");
                    initScript.Attributes.Add("type", "text/javascript");
                    var scriptTemplate = @"
						$(function(){
							SelectFormInit(""{{FieldId}}"",""{{Name}}"",{{ConfigJson}});
						});"                        ;
                    scriptTemplate = scriptTemplate.Replace("{{FieldId}}", (FieldId != null ? FieldId.Value.ToString() : ""));
                    scriptTemplate = scriptTemplate.Replace("{{Name}}", Name);

                    var fieldConfig = new WvFieldSelectConfig()
                    {
                        ApiUrl            = ApiUrl,
                        CanAddValues      = Access == WvFieldAccess.FullAndCreate ? true : false,
                        IsInvalid         = ValidationErrors.Count > 0,
                        AjaxDatasource    = AjaxDatasource,
                        AjaxDatasourceApi = AjaxDatasourceApi,
                        SelectMatchType   = SelectMatchType,
                        Placeholder       = Placeholder
                    };

                    scriptTemplate = scriptTemplate.Replace("{{ConfigJson}}", JsonConvert.SerializeObject(fieldConfig));

                    initScript.InnerHtml.AppendHtml(jsCompressor.Compress(scriptTemplate));

                    output.PostContent.AppendHtml(initScript);
                    #endregion


                    //TODO Implement CanAddValues
                    //@if (config.CanAddValues ?? false)
                    //{
                    //<div id="*****@*****.**" class="modal" data-backdrop="true">
                    //	<div class="modal-dialog" name="add-option">
                    //		<div class="modal-content">
                    //			<div class="modal-header">
                    //				<h5 class="modal-title">Add @(fieldMeta.Label)</h5>
                    //			</div>
                    //			<div class="modal-body">
                    //				<div class="alert alert-danger d-none"></div>
                    //				<div class="form-group">
                    //					<label class="control-label">New value</label>
                    //					<input class="form-control erp-select add-option-input" value="" required />
                    //				</div>
                    //			</div>
                    //			<div class="modal-footer">
                    //				<button class="btn btn-primary btn-sm" type="submit"><i class="fa fa-plus-circle"></i> Add</button>
                    //				<button class="btn btn-secondary btn-sm" data-dismiss="modal">Close</button>
                    //			</div>
                    //		</div>
                    //	</div>
                    //</div>

                    //}
                }
                else if (Access == WvFieldAccess.ReadOnly)
                {
                    //Have to render it as a normal select as readonly prop does not work with select 2. Also in order for the select not to work it should be disabled,
                    //which will not pass the value, this the hidden input

                    //Hidden input
                    var hiddenEl = new TagBuilder("input");
                    hiddenEl.Attributes.Add("id", $"input-{FieldId}");
                    hiddenEl.Attributes.Add("name", $"{Name}");
                    hiddenEl.Attributes.Add("value", (Value ?? "").ToString());
                    hiddenEl.Attributes.Add("type", "hidden");
                    output.Content.AppendHtml(hiddenEl);

                    var inputGroupEl = new TagBuilder("div");
                    if (PrependHtml.Count > 0 || AppendHtml.Count > 0)
                    {
                        inputGroupEl.AddCssClass("input-group");
                    }
                    else
                    {
                        inputGroupEl.AddCssClass("d-flex");
                    }
                    //Prepend
                    if (PrependHtml.Count > 0)
                    {
                        var prependEl = new TagBuilder("span");
                        prependEl.AddCssClass($"input-group-prepend {(ValidationErrors.Count > 0 ? "is-invalid" : "")}");
                        foreach (var htmlString in PrependHtml)
                        {
                            prependEl.InnerHtml.AppendHtml(htmlString);
                        }
                        inputGroupEl.InnerHtml.AppendHtml(prependEl);
                    }

                    //Dummy disabled select
                    var selectEl = new TagBuilder("select");
                    selectEl.Attributes.Add("id", $"select-{FieldId}");
                    selectEl.Attributes.Add("readonly", null);
                    selectEl.Attributes.Add("disabled", "disabled");
                    var inputElCssClassList = new List <string>();
                    inputElCssClassList.Add("form-control erp-select");
                    if (ValidationErrors.Count > 0)
                    {
                        inputElCssClassList.Add("is-invalid");
                    }
                    selectEl.Attributes.Add("class", String.Join(' ', inputElCssClassList));
                    if (Required)
                    {
                        selectEl.Attributes.Add("required", null);

                        if (String.IsNullOrWhiteSpace(Value))
                        {
                            var defaultOption = Options.FirstOrDefault(x => x.Value == DefaultValue);

                            if (defaultOption != null)
                            {
                                Value = DefaultValue;
                            }
                        }
                    }
                    else
                    {
                        var optionEl = new TagBuilder("option");
                        // Should work only with <option></option> and the select2 placeholder to be presented
                        //optionEl.Attributes.Add("value", "");
                        //if (String.IsNullOrWhiteSpace(Value))
                        //{
                        //    optionEl.Attributes.Add("selected", null);
                        //}
                        //optionEl.InnerHtml.Append("not selected");
                        selectEl.InnerHtml.AppendHtml(optionEl);
                    }

                    foreach (var option in Options)
                    {
                        var optionEl = new TagBuilder("option");
                        optionEl.Attributes.Add("value", option.Value);
                        if (option.Value == (Value ?? "").ToString())
                        {
                            optionEl.Attributes.Add("selected", null);
                        }
                        optionEl.Attributes.Add("data-icon", option.IconClass);
                        optionEl.Attributes.Add("data-color", option.Color);
                        optionEl.InnerHtml.Append(option.Label);
                        selectEl.InnerHtml.AppendHtml(optionEl);
                    }
                    inputGroupEl.InnerHtml.AppendHtml(selectEl);
                    //Append
                    if (AppendHtml.Count > 0)
                    {
                        var appendEl = new TagBuilder("span");
                        appendEl.AddCssClass($"input-group-append {(ValidationErrors.Count > 0 ? "is-invalid" : "")}");

                        foreach (var htmlString in AppendHtml)
                        {
                            appendEl.InnerHtml.AppendHtml(htmlString);
                        }
                        inputGroupEl.InnerHtml.AppendHtml(appendEl);
                    }

                    output.Content.AppendHtml(inputGroupEl);
                }
            }
            else if (Mode == WvFieldRenderMode.Display)
            {
                var valueString = (Value ?? "").ToString();
                if (!String.IsNullOrWhiteSpace(valueString))
                {
                    var formControlEl = new TagBuilder("div");
                    formControlEl.Attributes.Add("id", $"input-{FieldId}");
                    formControlEl.AddCssClass("form-control-plaintext erp-select");

                    var optionEl       = new TagBuilder("span");
                    var selectedOption = Options.FirstOrDefault(x => x.Value == valueString);
                    if (selectedOption == null)
                    {
                        optionEl.InnerHtml.Append(valueString);
                        if (Value != null)
                        {
                            var optionElIcon = new TagBuilder("span");
                            optionElIcon.AddCssClass("fa fa-fw fa-exclamation-circle go-red");
                            optionElIcon.Attributes.Add("title", "the value is not supported by this field anymore");
                            optionEl.InnerHtml.AppendHtml(optionElIcon);
                        }
                    }
                    else
                    {
                        optionEl.Attributes.Add("title", selectedOption.Label);
                        optionEl.Attributes.Add("data-key", valueString);
                        if (String.IsNullOrWhiteSpace(selectedOption.IconClass))
                        {
                            optionEl.InnerHtml.Append(selectedOption.Label);
                        }
                        else
                        {
                            var color = "#999";
                            if (!String.IsNullOrWhiteSpace(selectedOption.Color))
                            {
                                color = selectedOption.Color;
                            }

                            optionEl.InnerHtml.AppendHtml($"<i class=\"{selectedOption.IconClass}\" style=\"color:{color}\"></i> {selectedOption.Label}");
                        }
                    }

                    formControlEl.InnerHtml.AppendHtml(optionEl);

                    output.Content.AppendHtml(formControlEl);
                }
                else
                {
                    output.Content.AppendHtml(EmptyValEl);
                }
            }
            else if (Mode == WvFieldRenderMode.Simple)
            {
                output.SuppressOutput();
                var valueString = (Value ?? "").ToString();

                if (String.IsNullOrWhiteSpace(valueString))
                {
                    output.Content.AppendHtml("");
                }
                else
                {
                    var selectedOption = Options.FirstOrDefault(x => x.Value == valueString);
                    if (selectedOption == null)
                    {
                        output.Content.Append(valueString);
                        // in simple mode exclamation mark should not be rendered
                        //if (Value != null && (Value.ToString() != ""))
                        //{
                        //	var optionElIcon = new TagBuilder("span");
                        //	optionElIcon.AddCssClass("fa fa-fw fa-exclamation-circle go-red");
                        //	optionElIcon.Attributes.Add("title", "the value is not supported by this field anymore");
                        //	output.Content.AppendHtml(optionElIcon);
                        //}
                    }
                    else
                    {
                        if (String.IsNullOrWhiteSpace(selectedOption.IconClass))
                        {
                            output.Content.Append(selectedOption.Label);
                        }
                        else
                        {
                            var color = "#999";
                            if (!String.IsNullOrWhiteSpace(selectedOption.Color))
                            {
                                color = selectedOption.Color;
                            }

                            output.Content.AppendHtml($"<i class=\"{selectedOption.IconClass}\" style=\"color:{color}\"></i> {selectedOption.Label}");
                        }
                    }
                }
                return;
            }
            else if (Mode == WvFieldRenderMode.InlineEdit)
            {
                if (Access == WvFieldAccess.Full || Access == WvFieldAccess.FullAndCreate)
                {
                    #region << View Wrapper >>
                    {
                        var viewWrapperEl = new TagBuilder("div");
                        viewWrapperEl.AddCssClass("input-group view-wrapper");
                        viewWrapperEl.Attributes.Add("title", "double click to edit");
                        viewWrapperEl.Attributes.Add("id", $"view-{FieldId}");

                        //Prepend
                        if (PrependHtml.Count > 0)
                        {
                            var viewInputPrepend = new TagBuilder("span");
                            viewInputPrepend.AddCssClass("input-group-prepend");
                            foreach (var htmlString in PrependHtml)
                            {
                                viewInputPrepend.InnerHtml.AppendHtml(htmlString);
                            }
                            viewWrapperEl.InnerHtml.AppendHtml(viewInputPrepend);
                        }
                        //Control
                        var viewFormControlEl = new TagBuilder("div");
                        viewFormControlEl.AddCssClass("form-control erp-select");

                        var selectedOption = Options.FirstOrDefault(x => x.Value == (Value ?? "").ToString());
                        if (selectedOption == null)
                        {
                            viewFormControlEl.InnerHtml.Append((Value ?? "").ToString());
                            if (Value != null && (Value.ToString() != ""))
                            {
                                var optionElIcon = new TagBuilder("span");
                                optionElIcon.AddCssClass("fa fa-fw fa-exclamation-circle go-red");
                                optionElIcon.Attributes.Add("title", "the value is not supported by this field anymore");
                                viewFormControlEl.InnerHtml.AppendHtml(optionElIcon);
                            }
                        }
                        else
                        {
                            if (String.IsNullOrWhiteSpace(selectedOption.IconClass))
                            {
                                viewFormControlEl.InnerHtml.Append(selectedOption.Label);
                            }
                            else
                            {
                                var color = "#999";
                                if (!String.IsNullOrWhiteSpace(selectedOption.Color))
                                {
                                    color = selectedOption.Color;
                                }

                                viewFormControlEl.InnerHtml.AppendHtml($"<i class=\"{selectedOption.IconClass}\" style=\"color:{color}\"></i> {selectedOption.Label}");
                            }
                        }

                        viewWrapperEl.InnerHtml.AppendHtml(viewFormControlEl);

                        //Append
                        var viewInputActionEl = new TagBuilder("span");
                        viewInputActionEl.AddCssClass("input-group-append action");
                        foreach (var htmlString in AppendHtml)
                        {
                            viewInputActionEl.InnerHtml.AppendHtml(htmlString);
                        }
                        viewInputActionEl.InnerHtml.AppendHtml("<button type=\"button\" class='btn btn-white' title='edit'><i class='fa fa-fw fa-pencil-alt'></i></button>");
                        viewWrapperEl.InnerHtml.AppendHtml(viewInputActionEl);

                        /*
                         * Append an anchor field with the provided link value, if it is present
                         * Feature: LInkable Text Field
                         * Author: Amarjeet-L
                         */
                        if (Link != "" && Link != null)
                        {
                            var linkInputActionEl = new TagBuilder("span");
                            linkInputActionEl.AddCssClass("input-group-append");
                            foreach (var htmlString in AppendHtml)
                            {
                                linkInputActionEl.InnerHtml.AppendHtml(htmlString);
                            }
                            linkInputActionEl.InnerHtml.AppendHtml("<a href='" + Link + "' target='_blank' class='btn btn-white' title='details'><i class='fas fa-external-link-alt'></i></a>");
                            viewWrapperEl.InnerHtml.AppendHtml(linkInputActionEl);
                        }
                        output.Content.AppendHtml(viewWrapperEl);
                    }
                    #endregion

                    #region << Edit Wrapper>>
                    {
                        var editWrapperEl = new TagBuilder("div");
                        editWrapperEl.Attributes.Add("id", $"edit-{FieldId}");
                        editWrapperEl.Attributes.Add("style", $"display:none;");
                        editWrapperEl.AddCssClass("edit-wrapper");

                        var editInputGroupEl = new TagBuilder("div");
                        editInputGroupEl.AddCssClass("input-group");

                        //Prepend
                        if (PrependHtml.Count > 0)
                        {
                            var editInputPrepend = new TagBuilder("span");
                            editInputPrepend.AddCssClass("input-group-prepend");
                            foreach (var htmlString in PrependHtml)
                            {
                                editInputPrepend.InnerHtml.AppendHtml(htmlString);
                            }
                            editInputGroupEl.InnerHtml.AppendHtml(editInputPrepend);
                        }
                        //Control
                        var formControl         = new TagBuilder("div");
                        var inputElCssClassList = new List <string>();
                        inputElCssClassList.Add("form-control erp-select");
                        if (ValidationErrors.Count > 0)
                        {
                            inputElCssClassList.Add("is-invalid");
                        }
                        formControl.Attributes.Add("class", String.Join(' ', inputElCssClassList));

                        var selectEl = new TagBuilder("select");
                        selectEl.Attributes.Add("id", $"input-{FieldId}");
                        selectEl.Attributes.Add("name", $"{Name}");

                        var emptyOptionAdded = false;
                        if (Required)
                        {
                            selectEl.Attributes.Add("required", null);
                        }
                        else
                        {
                            var optionEl = new TagBuilder("option");
                            // Should work only with <option></option> and the select2 placeholder to be presented
                            selectEl.InnerHtml.AppendHtml(optionEl);
                            emptyOptionAdded = true;
                        }

                        selectEl.Attributes.Add("data-original-value", JsonConvert.SerializeObject((Value ?? "").ToString()));

                        foreach (var option in Options)
                        {
                            var optionEl = new TagBuilder("option");
                            optionEl.Attributes.Add("value", option.Value);
                            optionEl.Attributes.Add("data-icon", option.IconClass);
                            optionEl.Attributes.Add("data-color", option.Color);
                            if (option.Value == (Value ?? "").ToString())
                            {
                                optionEl.Attributes.Add("selected", null);
                            }
                            optionEl.InnerHtml.Append(option.Label);
                            selectEl.InnerHtml.AppendHtml(optionEl);
                        }

                        //At least one option should be in the select so it can submit
                        if (!emptyOptionAdded && Options.Count == 0)
                        {
                            var optionEl = new TagBuilder("option");
                            // Should work only with <option></option> and the select2 placeholder to be presented
                            selectEl.InnerHtml.AppendHtml(optionEl);
                        }

                        formControl.InnerHtml.AppendHtml(selectEl);
                        editInputGroupEl.InnerHtml.AppendHtml(formControl);

                        //Append
                        var editInputGroupAppendEl = new TagBuilder("span");
                        editInputGroupAppendEl.AddCssClass("input-group-append");

                        foreach (var htmlString in AppendHtml)
                        {
                            editInputGroupAppendEl.InnerHtml.AppendHtml(htmlString);
                        }
                        editInputGroupAppendEl.InnerHtml.AppendHtml("<button type=\"button\" class='btn btn-white save' title='save'><i class='fa fa-fw fa-check go-green'></i></button>");
                        editInputGroupAppendEl.InnerHtml.AppendHtml("<button type=\"button\" class='btn btn-white cancel' title='cancel'><i class='fa fa-fw fa-times go-gray'></i></button>");
                        editInputGroupEl.InnerHtml.AppendHtml(editInputGroupAppendEl);

                        editWrapperEl.InnerHtml.AppendHtml(editInputGroupEl);

                        output.Content.AppendHtml(editWrapperEl);
                    }
                    #endregion

                    var jsCompressor = new JavaScriptCompressor();

                    #region << Init Select2 >>
                    {
                        var wvLibraryInitialized = false;
                        var libraryItemsKey      = "WebVella-" + "select2";
                        if (ViewContext.HttpContext.Items.ContainsKey(libraryItemsKey))
                        {
                            var tagHelperContext = (WvTagHelperContext)ViewContext.HttpContext.Items[libraryItemsKey];
                            wvLibraryInitialized = tagHelperContext.Initialized;
                        }

                        if (!wvLibraryInitialized)
                        {
                            {
                                var libCssEl = new TagBuilder("link");
                                libCssEl.Attributes.Add("href", "/_content/WebVella.TagHelpers/lib/select2/css/select2.min.css");
                                libCssEl.Attributes.Add("type", "text/css");
                                libCssEl.Attributes.Add("rel", "stylesheet");
                                output.PostContent.AppendHtml(libCssEl);
                                output.PostContent.AppendHtml("\r\n\t");
                            }
                            {
                                var libCssEl = new TagBuilder("link");
                                libCssEl.Attributes.Add("href", "/_content/WebVella.TagHelpers/lib/select2-bootstrap-theme/select2-bootstrap4.css");
                                libCssEl.Attributes.Add("type", "text/css");
                                libCssEl.Attributes.Add("rel", "stylesheet");
                                output.PostContent.AppendHtml(libCssEl);
                                output.PostContent.AppendHtml("\r\n\t");
                            }

                            var libJsEl = new TagBuilder("script");
                            libJsEl.Attributes.Add("type", "text/javascript");
                            libJsEl.Attributes.Add("src", "/_content/WebVella.TagHelpers/lib/select2/js/select2.min.js");
                            output.PostContent.AppendHtml(libJsEl);
                            output.PostContent.AppendHtml("\r\n\t");

                            ViewContext.HttpContext.Items[libraryItemsKey] = new WvTagHelperContext()
                            {
                                Initialized = true
                            };
                        }
                    }
                    #endregion


                    #region << Init Scripts >>
                    var tagHelperInitialized = false;
                    if (ViewContext.HttpContext.Items.ContainsKey(typeof(WvFieldSelect) + "-inline-edit"))
                    {
                        var tagHelperContext = (WvTagHelperContext)ViewContext.HttpContext.Items[typeof(WvFieldSelect) + "-inline-edit"];
                        tagHelperInitialized = tagHelperContext.Initialized;
                    }
                    if (!tagHelperInitialized)
                    {
                        var scriptContent = WvHelpers.GetEmbeddedTextResource("inline-edit.js", "WebVella.TagHelpers.TagHelpers.WvFieldSelect", "WebVella.TagHelpers");
                        var scriptEl      = new TagBuilder("script");
                        scriptEl.Attributes.Add("type", "text/javascript");
                        //scriptEl.InnerHtml.AppendHtml(jsCompressor.Compress(scriptContent));
                        scriptEl.InnerHtml.AppendHtml(scriptContent);
                        output.PostContent.AppendHtml(scriptEl);

                        ViewContext.HttpContext.Items[typeof(WvFieldSelect) + "-inline-edit"] = new WvTagHelperContext()
                        {
                            Initialized = true
                        };
                    }
                    #endregion

                    #region << Add Inline Init Script for this instance >>
                    var initScript = new TagBuilder("script");
                    initScript.Attributes.Add("type", "text/javascript");
                    var scriptTemplate = @"
						$(function(){
							SelectInlineEditInit(""{{FieldId}}"",""{{Name}}"",{{ConfigJson}});
						});"                        ;
                    scriptTemplate = scriptTemplate.Replace("{{FieldId}}", (FieldId != null ? FieldId.Value.ToString() : ""));
                    scriptTemplate = scriptTemplate.Replace("{{Name}}", Name);


                    var fieldConfig = new WvFieldSelectConfig()
                    {
                        ApiUrl            = ApiUrl,
                        CanAddValues      = Access == WvFieldAccess.FullAndCreate ? true : false,
                        IsInvalid         = ValidationErrors.Count > 0,
                        AjaxDatasource    = AjaxDatasource,
                        AjaxDatasourceApi = AjaxDatasourceApi,
                        SelectMatchType   = SelectMatchType,
                        Placeholder       = Placeholder
                    };

                    scriptTemplate = scriptTemplate.Replace("{{ConfigJson}}", JsonConvert.SerializeObject(fieldConfig));

                    initScript.InnerHtml.AppendHtml(jsCompressor.Compress(scriptTemplate));

                    output.PostContent.AppendHtml(initScript);
                    #endregion
                }
                else if (Access == WvFieldAccess.ReadOnly)
                {
                    var divEl = new TagBuilder("div");
                    divEl.AddCssClass("input-group");

                    //Prepend
                    if (PrependHtml.Count > 0)
                    {
                        var viewInputPrepend = new TagBuilder("span");
                        viewInputPrepend.AddCssClass("input-group-prepend");
                        foreach (var htmlString in PrependHtml)
                        {
                            viewInputPrepend.InnerHtml.AppendHtml(htmlString);
                        }
                        divEl.InnerHtml.AppendHtml(viewInputPrepend);
                    }
                    //Control
                    var formControlEl = new TagBuilder("div");
                    formControlEl.AddCssClass("form-control erp-select");

                    var optionEl = new TagBuilder("span");
                    optionEl.Attributes.Add("selected", null);
                    var selectedOption = Options.FirstOrDefault(x => x.Value == (Value ?? "").ToString());
                    if (selectedOption == null)
                    {
                        optionEl.InnerHtml.Append((Value ?? "").ToString());
                        if (Value != null && (Value.ToString() != ""))
                        {
                            var optionElIcon = new TagBuilder("span");
                            optionElIcon.AddCssClass("fa fa-fw fa-exclamation-circle go-red");
                            optionElIcon.Attributes.Add("title", "the value is not supported by this field anymore");
                            optionEl.InnerHtml.AppendHtml(optionElIcon);
                        }
                    }
                    else
                    {
                        optionEl.Attributes.Add("title", selectedOption.Label);
                        optionEl.Attributes.Add("data-key", (Value ?? "").ToString());
                        if (String.IsNullOrWhiteSpace(selectedOption.IconClass))
                        {
                            optionEl.InnerHtml.Append(selectedOption.Label);
                        }
                        else
                        {
                            var color = "#999";
                            if (!String.IsNullOrWhiteSpace(selectedOption.Color))
                            {
                                color = selectedOption.Color;
                            }

                            optionEl.InnerHtml.AppendHtml($"<i class=\"{selectedOption.IconClass}\" style=\"color:{color}\"></i> {selectedOption.Label}");
                        }
                    }
                    formControlEl.InnerHtml.AppendHtml(optionEl);

                    divEl.InnerHtml.AppendHtml(formControlEl);
                    //Append
                    var appendActionSpan = new TagBuilder("span");
                    appendActionSpan.AddCssClass("input-group-append");
                    foreach (var htmlString in AppendHtml)
                    {
                        appendActionSpan.InnerHtml.AppendHtml(htmlString);
                    }
                    appendActionSpan.InnerHtml.AppendHtml("<button type=\"button\" disabled class='btn btn-white' title='locked'><i class='fa fa-fw fa-lock'></i></button>");
                    divEl.InnerHtml.AppendHtml(appendActionSpan);

                    output.Content.AppendHtml(divEl);
                }
            }
            #endregion


            //Finally
            if (SubInputEl != null)
            {
                output.PostContent.AppendHtml(SubInputEl);
            }

            return;
        }