none
Recuperar IEnumerable de la vista al controlador

    Question

  • Hola A Todos!!

    Necesito su ayuda amigos!

    Tengo una vista a la cual le paso una lista de estudiantes de un curso en especifico.

    En la vista mi usuario solo ingresara las notas de cada uno de los estudiantes y luego presionara guardar.

    Ahora nose como recuperar desde mi controlador POST esa lista de estudiantes. El campo de texto lo recupero con FormCollection pero la lista nose.

    Les paso mi accion del Controlador GET

    public ActionResult CrearNotaEstudiantesGlobal(string CursoID, string MateriaID)
            {
                try
                {
                    cursoid = CursoID;
                    materiaid = MateriaID;

                    //materia
                    var materia = from p in db.Materia
                                  select p;

                    //estudiante
                    var estudiante = from p in db.Estudiante.Include("Curso")
                                     select p;


                    //ViewBag.CursoID = new SelectList(db.Curso, "CodigoCurso", "NombreCurso");
                    var curso = db.Curso;
                    //recuperamos el codigo del docente actual si coincide con el usuario actual
                    var codigodelcurso = db.Curso.Single(c => c.CodigoCurso == CursoID);

                    string cursocodigo = codigodelcurso.CodigoCurso;



                    if (!String.IsNullOrEmpty(CursoID))
                    {
                        //string int idcategoria = Convert.ToInt32(CursoID);
                        estudiante = estudiante.Where(x => x.CodigoCurso == CursoID);

                        ViewBag.Curso = codigodelcurso.NombreCurso;

                    }
                    return View(estudiante.ToList());

                }
                catch (Exception e)
                {
                    //Si se introduce un error de direccion http no existente, devolvemos a la vista el error generado
                    ViewData["msg"] = e.Message;
                    return View("Error");
                }
            }

    MI VISTA

                    

    @model IEnumerable<SiamLuisEQuispeRojas.Models.Estudiante>

    @{
        ViewBag.Title = "CrearNotaEstudiantesGlobal";
        Layout = "~/Views/Shared/_Layout.cshtml";
    }

    <h2>CrearNotaEstudiantesGlobal</h2>

    <p>
        @Html.ActionLink("Create New", "Create")
    </p>

         @using (Html.BeginForm())

         {
               @Html.ValidationSummary(true)  

     <table>
        <tr>
            <th>
                ApellidoPaterno
            </th>
            <th>
                ApellidoMaterno
            </th>
            <th>
                Nombres
            </th>
            <th></th>
        </tr>

    @foreach (var item in Model)
    {
        <tr>
            <td>
                @Html.DisplayFor(modelItem => item.ApellidoPaterno)
            </td>
            <td>
                @Html.DisplayFor(modelItem => item.ApellidoMaterno)
            </td>
            <td>
                @Html.DisplayFor(modelItem => item.Nombres)
            </td>
            <td>
                @Html.TextBox("NotaPrimero")
            </td>
        </tr>
    }

    </table>
         <input type="submit" value="Guardar" /> 
             }

    Y MI ACCION POST

                                         

    [HttpPost]
            public ActionResult CrearNotaEstudiantesGlobal(IEnumerable<Estudiante> model, FormCollection form)
            {
                try
                {
                    Nota nota = new Nota();

    //recuperamos la coleccion de notas en el textbox "NotaPrimero"

                    string tags = form["NotaPrimero"];
                    char[] delimitadores = { ' ', ',', '.', ';' };
                    string[] TagsString = tags.Split(delimitadores);
                    foreach (String tagtexto in TagsString)
                    {
                        if (!String.IsNullOrEmpty(cursoid))
                        {
    //deberia recuperar aki el codigo del estudiante, solamente el codigo y nose como

                            nota.CodigoMateria = materiaid;
                            nota.Nota1 = Convert.ToDecimal(tagtexto);

                        }

                    }


    Agradezco sus respuestas!!!!


    Luis

    Saturday, December 01, 2012 9:51 PM

All replies

  • hola???

    Luis

    Sunday, December 02, 2012 8:14 PM
  • Hola Luis, creo que podrias probar enviar la lista desde el formulario usando algo asi:

    @using (Html.BeginForm("CrearNotaEstudiantesGlobal", "NombreDeTuControlador", new{ model= Model}))

    ojala sirva.

    Saludos

    Monday, December 03, 2012 11:50 AM
  • MMmm...

    La solución de @Richof no creo que funcione... El Html.BeginForm usará el ToString() para convertir el Model a una cadena, y el Model es un IEnumerable<T>.

    Probablemente recibas null como valor del parámetro model, no?

    Estás combinando varios errores en uno solo:

    1. En el controlador el parámetro se llama model, pero tu en la vista usas como nombre de parámetro item (item.Nombres, item.ApellidoMaterno, etc). Deben llamarse igual.
    2. En la vista usas @Html.DisplayFor. Ojo con él, porque puede renderizarse a texto, es decir puede renderizarse a un elemento que "no se envíe por POST". Usa @Html.TextBoxFor si quieres que sea un textbox y se envíe (añádele el atributo readonly para que sea de solo lectura).
    3. Estás generando N veces el "mismo control". Es decir todas las llamadas a @Html.EditorFor(modelItem => item.ApellidoMaterno) van a generar el mismo <input> con el mismo name y el mismo ID.
    4. Relacionado con (3): el Model Binder de ASP.NET MVC no sabe inferir que N campos llamados igual conforman una colección, así que debes llamar a los campos model[0], model[1], etc. Para ello puedes usar un código parecido a:
    var model = Model.ToList();
    for (var idx=0; idx<Model.Count(); idx++)
    {
        <tr>
            <td>
                @Html.EditorFor(modelItem => model[idx].ApellidoPaterno)
            </td>
            <td>
                @Html.EditorFor(modelItem => model[idx].ApellidoMaterno)
            </td>
            <td>
                @Html.EditorFor(modelItem => model[idx].Nombres)
            </td>
            <td>
                @Html.TextBox("NotaPrimero")
            </td>
        </tr>
    }

    Ya me dirás!
    Saludos!


    Eduard Tomàs Blog: http://geeks.ms/blogs/etomas -- Twitter: eiximenis

    Monday, December 03, 2012 4:54 PM
  • Me parece que Eduard anda por buen camino.  Le cuento cómo yo he logrado recibir una lista en un controlador:

    1. Creo una vista con @model IEnumerable<Clase> según el código mostrado abajo.
    2. Creo una acción de controlador para HttpPost con la fima:  public ActionResult NombreDeAccion(List<Clase> objetos).
    3. Creo una vista parcial con @model Clase en ~/Views/Shared/EditorTemplates (porque asumo que es para editar).  Se llama Clase.cshtml.  Ver abajo.
    @model IEnumerable<Clase>
    
    @using (Html.BeginForm())
    {
        @Html.EditorForModel()
    }

    @model Clase
    
    <div>
        @Html.EditorFor(m => m.Propiedad)<br />
        @Html.EditorFor(m => m.OtraPropiedad)<br />
        ...
    </div>

    Me parece que así el motor de MVC hace automáticamente lo que comenta Eduard.


    Jose R. MCP
    Code Samples

    Monday, December 03, 2012 5:14 PM