Как отправить начальную форму бритвы MVC с динамически созданными элементами только для чтения

Я пытаюсь создать форму, которая будет динамически создавать входные данные только для чтения с использованием javascript и передавать эти значения вместе со значениями модели в контроллер, но мой FormCollection в моем методе контроллера содержит только значения модели, а не входные значения. Любая помощь в том, что я делаю неправильно, была бы потрясающей. Вот мой код:

Model.Courses содержит тип CourseId и строку CourseName. Я создаю входные данные только для чтения со значением CourseName для передачи в FormCollection, чтобы установить порядок курсов, содержащихся в каждом учебном лагере.

Вид:

    <div class = "container">
<div class = "row">
    <div class = "col-xs-12">
        <h2>Create Bootcamp</h2>

        @using (Html.BeginForm("Create", "LMSBootcamp", FormMethod.Post))
        {
            @Html.AntiForgeryToken()

            <div class = "form-horizontal">
                <hr />
                @Html.ValidationSummary(true, "", new { @class = "text-danger" })

                <div class = "form-group">
                    @Html.LabelFor(model => model.Title, htmlAttributes: new { @class = "control-label col-md-2" })
                    <div class = "col-md-10">
                        @Html.EditorFor(model => model.Title, new { htmlAttributes = new { @class = "form-control" } })
                        @Html.ValidationMessageFor(model => model.Title, "", new { @class = "text-danger" })
                    </div>
                </div>

                <div class = "row">
                    <div class = "col-xs-6 w-50">
                        <h5>Course Order</h5>
                        <ol id = "orderContainer">

                        </ol>
                    </div>
                    <div class = "col-xs-6 w-50">
                        <h5>Available Courses</h5>
                        <ul>
                            @foreach (var course in Model.Courses.OrderBy(a=>a.CourseName))
                            {
                                <li id = "@course.CourseId" onclick = "Add_Course()" data-arg = "@course.CourseId">@course.CourseName</li>
                            }
                        </ul>
                    </div>
                </div>
                


                <div class = "form-group">
                    <div class = "col-md-offset-2 col-md-10">
                        <input type = "submit" value = "Create" class = "btn btn-default" />
                    </div>
                </div>
            </div>
        }

        <div>
            @Html.ActionLink("Back to List", "Index")
        </div>
    </div>
</div>
<script type = "text/javascript">
function Add_Course() {
    var courseName = event.target.innerHTML;
    var courseId = event.target.getAttribute('data-arg');

    //create the readonly input for the course desired
    var order = document.createElement("input");
    order.readOnly = true;
    order.setAttribute("type", "text");
    order.setAttribute("value", courseName);
    order.classList.add("form-control", "text-box", "single-line");

    //create li element
    var listElement = document.createElement("li");
    listElement.onclick = function Remove_Course() {
        var element = event.target
        element.remove();
    }
    //add input to list element
    listElement.appendChild(order);

    //add list element to container
    var orderContainer = document.getElementById("orderContainer");
    orderContainer.appendChild(listElement);
}

Контроллер:

 [HttpPost]
    [ValidateAntiForgeryToken]
    public async Task<ActionResult> Create(FormCollection courseOrder)
    {
        
        return RedirectToAction("Index");
    }

Спасибо!

Ваши динамически создаваемые элементы ввода нуждаются в атрибуте name.

Jasen 12.12.2020 01:20
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
В JavaScript одним из самых запутанных понятий является поведение ключевого слова "this" в стрелочной и обычной функциях.
Концепция локализации и ее применение в приложениях React ⚡️
Концепция локализации и ее применение в приложениях React ⚡️
Локализация - это процесс адаптации приложения к различным языкам и культурным требованиям. Это позволяет пользователям получить опыт, соответствующий...
Улучшение производительности загрузки с помощью Google Tag Manager и атрибута Defer
Улучшение производительности загрузки с помощью Google Tag Manager и атрибута Defer
В настоящее время производительность загрузки веб-сайта имеет решающее значение не только для удобства пользователей, но и для ранжирования в...
Безумие обратных вызовов в javascript [JS]
Безумие обратных вызовов в javascript [JS]
Здравствуйте! Юный падаван 🚀. Присоединяйся ко мне, чтобы разобраться в одной из самых запутанных концепций, когда вы начинаете изучать мир...
Система управления парковками с использованием HTML, CSS и JavaScript
Система управления парковками с использованием HTML, CSS и JavaScript
Веб-сайт по управлению парковками был создан с использованием HTML, CSS и JavaScript. Это простой сайт, ничего вычурного. Основная цель -...
JavaScript Вопросы с множественным выбором и ответы
JavaScript Вопросы с множественным выбором и ответы
Если вы ищете платформу, которая предоставляет вам бесплатный тест JavaScript MCQ (Multiple Choice Questions With Answers) для оценки ваших знаний,...
1
1
377
2
Перейти к ответу Данный вопрос помечен как решенный

Ответы 2

Перед отправкой убедитесь, что эти динамически добавленные входные данные имеют правильные имена моделей, и все будет в порядке. Итак, в вашем примере это будет что-то похожее на это:

<input type = "text" name = "courseName[0]" value = "courseName 1"/>
<input type = "text" name = "courseName[1]" value = "courseName 2"/>
<input type = "text" name = "courseName[3]" value = "courseName 3"/>

И связыватель модели автоматически создаст список строк с этими 3 строками ("courseName 1", "courseName 2", "courseName 3") и назначит его соответствующему свойству, в данном случае значение.

Ответ принят как подходящий

Вот демо:

Модели:

public class FormModel {
        public string Title { get; set; }
        public List<Course> Courses { get; set; }
    }
    public class Course {
        public int CourseId { get; set; }
        public string CourseName { get; set; }

    }

Просмотр (перед отправкой формы добавьте имя к каждому добавленному вводу):

@model FormModel


        <div class = "row">
            <div class = "col-xs-12">
                <h2>Create Bootcamp</h2>

                @using (Html.BeginForm("Create", "LMSBootcamp", FormMethod.Post, new { id = "myForm" }))
                {
                    @Html.AntiForgeryToken()

                    <div class = "form-horizontal">
                        <hr />
                        @Html.ValidationSummary(true, "", new { @class = "text-danger" })

                        <div class = "form-group">
                            @Html.LabelFor(model => model.Title, htmlAttributes: new { @class = "control-label col-md-2" })
                            <div class = "col-md-10">
                                @Html.EditorFor(model => model.Title, new { htmlAttributes = new { @class = "form-control" } })
                                @Html.ValidationMessageFor(model => model.Title, "", new { @class = "text-danger" })
                            </div>
                        </div>

                        <div class = "row">
                            <div class = "col-xs-6 w-50">
                                <h5>Course Order</h5>
                                <ol id = "orderContainer">
                                </ol>
                            </div>
                            <div class = "col-xs-6 w-50">
                                <h5>Available Courses</h5>
                                <ul>
                                    @foreach (var course in Model.Courses.OrderBy(a => a.CourseName))
                                    {
                                        <li id = "@course.CourseId" onclick = "Add_Course()" data-arg = "@course.CourseId">@course.CourseName</li>
                                    }
                                </ul>
                            </div>
                        </div>



                        <div class = "form-group">
                            <div class = "col-md-offset-2 col-md-10">
                                <input type = "submit" value = "Create" class = "btn btn-default" />
                            </div>
                        </div>
                    </div>
                }

                <div>
                    @Html.ActionLink("Back to List", "Index")
                </div>
            </div>
        </div>
        @section scripts{
            <script type = "text/javascript">
                function Add_Course() {
                    var courseName = event.target.innerHTML;
                    var courseId = event.target.getAttribute('data-arg');

                    //create the readonly input for the course desired
                    var order = document.createElement("input");
                    order.readOnly = true;
                    order.setAttribute("type", "text");
                    order.setAttribute("value", courseName);
                    order.classList.add("form-control", "text-box", "single-line");

                    //create li element
                    var listElement = document.createElement("li");
                    listElement.onclick = function Remove_Course() {
                        var element = event.target
                        element.remove();
                    }
                    //add input to list element
                    listElement.appendChild(order);

                    //add list element to container
                    var orderContainer = document.getElementById("orderContainer");
                    orderContainer.appendChild(listElement);
                }
                //add name before form submit
                $('#myForm').submit(function () {
                    var i = 0;
                    $("#orderContainer li").each(function () {
                        $(this).find("input").attr("name", "courseName[" + i+"]");
                        i++;
                    })
                    // DO STUFF...
                    return true; // return false to cancel form action
                });
    </script>
}

Контроллер:

[HttpPost]
        [ValidateAntiForgeryToken]
        public async Task<ActionResult> Create(FormCollection courseOrder)
        {

            return Ok();
        }

результат:

Другие вопросы по теме