Dynamic plus form

 view:

@model ResumeManager.Models.Applicant


@{

    ViewData["Title"] = "Create";

}


<h1>Create</h1>


<h4>Applicant</h4>

<hr />

<div class="row">

    <div class="col-md-4">

        <form asp-action="Create">

            <div asp-validation-summary="ModelOnly" class="text-danger"></div>

            <div class="form-group">

                <label asp-for="Name" class="control-label"></label>

                <input asp-for="Name" class="form-control" />

                <span asp-validation-for="Name" class="text-danger"></span>

            </div>

            <div class="form-group">

                <label asp-for="Gender" class="control-label"></label>

                <input asp-for="Gender" class="form-control" />

                <span asp-validation-for="Gender" class="text-danger"></span>

            </div>

            <div class="form-group">

                <label asp-for="Age" class="control-label"></label>

                <input asp-for="Age" class="form-control" />

                <span asp-validation-for="Age" class="text-danger"></span>

            </div>

            <div class="form-group">

                <label asp-for="Qualification" class="control-label"></label>

                <input asp-for="Qualification" class="form-control" />

                <span asp-validation-for="Qualification" class="text-danger"></span>

            </div>

            <div class="form-group">

                <label asp-for="TotalExperience" class="control-label"></label>

                <input asp-for="TotalExperience" class="form-control" />

                <span asp-validation-for="TotalExperience" class="text-danger"></span>

            </div>



            <table id="ExpTable" class="table table-striped table-sm">

<thead>

<tr>

<th>

   CompanyName

</th>

<th>

   Designation

</th>

<th>

  YearsWorked.

</th>


<th>


</th>

</tr>

</thead>


<tbody>

@*@foreach(var item in Model.Experiences)*@

@for(int i=0; i < Model.Experiences.Count; i++)

{

  <tr>

    <td>

     @*<input asp-for="@item.CompanyName" class="form-control" />*@

     @Html.EditorFor( x=> x.Experiences[i].CompanyName,new { AddHtmlAttributes = new {@class = "form-control"}})

    </td>

    <td>

        @Html.EditorFor( x=> x.Experiences[i].Designation,new { AddHtmlAttributes = new {@class = "form-control"}})

    @*<input asp-for="@item.Designation" class="form-control" />*@

    </td>

    <td>

        @Html.EditorFor( x=> x.Experiences[i].Designation,new { AddHtmlAttributes = new {@class = "form-control"}})

     @*<input asp-for="@item.YearsWorked" class="form-control" />*@

    </td>

    <td>

        <button id="btnadd-@i" type="button" class="btn btn-sm btn-secondary visible" 

        onclick="AddItem(this)" >Add</button>

        <button id="btnremove-@i" type="button" class="btn btn-sm btn-secondary invisible"

        onclick="DeleteItem(this)">DELETE</button>

    </td>

  </tr>

}

</tbody>

</table>


<input type="hidden" id="hdnLastIndex" value="0" />


            <div class="form-group">

                <input type="submit" value="Create" class="btn btn-primary" />

            </div>

        </form>

    </div>

</div>


<div>

    <a asp-action="Index">Back to List</a>

</div>


@section Scripts {

    @{await Html.RenderPartialAsync("_ValidationScriptsPartial");}

}


    <script type="text/javascript">

$(".custom-file-input").on("change", function () {

var fileName = $(this).val().split("\\").pop();

$(this).siblings(".custom-file-label").addClass("selected").html(fileName);

});


        function DeleteItem(btn) {

$(btn).closest('tr').remove();

}


function AddItem(btn) {


var table = document.getElementById('ExpTable');

var rows = table.getElementsByTagName('tr');


var rowOuterHtml = rows[rows.length - 1].outerHTML;


            var lastrowIdx = document.getElementById('hdnLastIndex').value;


var nextrowIdx = eval(lastrowIdx) + 1;


document.getElementById('hdnLastIndex').value = nextrowIdx;


rowOuterHtml = rowOuterHtml.replaceAll('_' + lastrowIdx + '_', '_' + nextrowIdx + '_');

rowOuterHtml = rowOuterHtml.replaceAll('[' + lastrowIdx + ']', '[' + nextrowIdx + ']');

rowOuterHtml = rowOuterHtml.replaceAll('-' + lastrowIdx, '-' + nextrowIdx);


var newRow = table.insertRow();

            newRow.innerHTML = rowOuterHtml;



            var btnAddID = btn.id;

var btnDeleteid = btnAddID.replaceAll('btnadd', 'btnremove');


var delbtn = document.getElementById(btnDeleteid);

delbtn.classList.add("visible");

delbtn.classList.remove("invisible");



var addbtn = document.getElementById(btnAddID);

addbtn.classList.remove("visible");

addbtn.classList.add("invisible");

}


</script>



--controller

using Microsoft.AspNetCore.Http;

using Microsoft.AspNetCore.Mvc;

using ResumeManager.Models;

using ResumeManager.Data;

namespace ResumeManager.Controllers

{

    public class ResumeController : Controller

    {

        // GET: ResumeController


        private readonly ResumeDBContext _context;


        public ResumeController(ResumeDBContext context)

        {

            _context = context;

        }


        public ActionResult Index()

        {

            List<Applicant> applicants;


            applicants = _context.Applicants.ToList();


            return View(applicants);

        }


        // GET: ResumeController/Details/5

        public ActionResult Details(int id)

        {

            return View();

        }


        // GET: ResumeController/Create

        public ActionResult Create()

        {


            Applicant applicant=new Applicant();

            applicant.Experiences.Add(new Experience() { ExperienceId = 1 });

            //applicant.Experiences.Add(new Experience() { ExperienceId = 2 });

            //applicant.Experiences.Add(new Experience() { ExperienceId = 3 });



            return View(applicant);

        }


        // POST: ResumeController/Create

        [HttpPost]

        [ValidateAntiForgeryToken]

        public ActionResult Create(Applicant applicant)

        {

            try

            {

                _context.Add(applicant);

                _context.SaveChanges();

                return RedirectToAction(nameof(Index));

            }

            catch

            {

                return View();

            }

        }


        // GET: ResumeController/Edit/5

        public ActionResult Edit(int id)

        {

            return View();

        }


        // POST: ResumeController/Edit/5

        [HttpPost]

        [ValidateAntiForgeryToken]

        public ActionResult Edit(int id, IFormCollection collection)

        {

            try

            {

                return RedirectToAction(nameof(Index));

            }

            catch

            {

                return View();

            }

        }


        // GET: ResumeController/Delete/5

        public ActionResult Delete(int id)

        {

            return View();

        }


        // POST: ResumeController/Delete/5

        [HttpPost]

        [ValidateAntiForgeryToken]

        public ActionResult Delete(int id, IFormCollection collection)

        {

            try

            {

                return RedirectToAction(nameof(Index));

            }

            catch

            {

                return View();

            }

        }

    }

}



--models
applicant
using System.ComponentModel.DataAnnotations;
using System.ComponentModel.DataAnnotations.Schema;

namespace ResumeManager.Models
{
    public class Applicant
    {
        [Key]
        public int Id { get; set; }
        [Required]
        [StringLength(150)]
        public string Name { get; set; } = "";

        [Required]
        [StringLength(10)]
        public string  Gender { get; set; } = "";

        [Required]
        [Range(25,55,ErrorMessage = ("Currently,We have no Positions Vacant for your age"))]
        [Display(Name="Age in Years.")]
        public int Age { get; set; }

        [Required]
        [StringLength(50)]
        public string Qualification { get; set; } = "";

        [Required]
        [Range(1, 25, ErrorMessage = "Currently,We Have no Positions Vacant for Your Experience")]
        [Display(Name="Total Experience in Years")]
        public int TotalExperience { get; set; }

        public virtual List<Experience> Experiences { get; set; } = new List<Experience>();//detail very important

        //public string PhotoUrl { get; set; }

        //[Required(ErrorMessage = "Please choose the Profile Photo")]
        //[Display(Name = "Profile Photo")]
        //[NotMapped]
        //public IFormFile ProfilePhoto { get; set; }


    }
}

--
experiences

using System.ComponentModel.DataAnnotations;
using System.ComponentModel.DataAnnotations.Schema;

namespace ResumeManager.Models
{
    public class Applicant
    {
        [Key]
        public int Id { get; set; }
        [Required]
        [StringLength(150)]
        public string Name { get; set; } = "";

        [Required]
        [StringLength(10)]
        public string  Gender { get; set; } = "";

        [Required]
        [Range(25,55,ErrorMessage = ("Currently,We have no Positions Vacant for your age"))]
        [Display(Name="Age in Years.")]
        public int Age { get; set; }

        [Required]
        [StringLength(50)]
        public string Qualification { get; set; } = "";

        [Required]
        [Range(1, 25, ErrorMessage = "Currently,We Have no Positions Vacant for Your Experience")]
        [Display(Name="Total Experience in Years")]
        public int TotalExperience { get; set; }

        public virtual List<Experience> Experiences { get; set; } = new List<Experience>();//detail very important

        //public string PhotoUrl { get; set; }

        //[Required(ErrorMessage = "Please choose the Profile Photo")]
        //[Display(Name = "Profile Photo")]
        //[NotMapped]
        //public IFormFile ProfilePhoto { get; set; }


    }
}


Comments