0

I am trying to get to grips with MVC and trying to populate a strongly typed dropdown list. I intend to have many dropdown controls on the index page and to keep things tidy I would like to use a different model for each dropdown and then have all these with the home index model.

When building the application I get the error "ViewModels.HomeIndex.TrackModel.get returned null."

enter image description here

When I set a breakpoint I can see the TrackModel is not empty, however the TrackId and TrackName are. I guess it is this that is causing the issue.

Anyone more familure with MVC see what may be wrong.

enter image description here

In my controller I have

public class HomeController : Controller
{      

    public ActionResult Index()
    {           
        TrackModel tm = new TrackModel();
        tm.Tracks = PopulateTracks();

        return View(new HomeIndex());
    }

    [HttpPost]
    public ActionResult Index(TrackModel tm)
    {
        tm.Tracks = PopulateTracks();
        var selectedItem = tm.Tracks.Find(p => p.Value == tm.TrackId.ToString());
        if (selectedItem != null)
        {
            selectedItem.Selected = true;
            ViewBag.Message = "Track: " + selectedItem.Text;
            ViewBag.Message += "\\TrackName: " + tm.TrackName;
        }

        return View(tm);
    }

    private static List<SelectListItem> PopulateTracks()
    {
        List<SelectListItem> items = new List<SelectListItem>();
        string constr = ConfigurationManager.ConnectionStrings["AiryDb"].ConnectionString;
        using (SqlConnection con = new SqlConnection(constr))
        {
            string query = "SELECT UserId, TrackName FROM UploadData";
            using (SqlCommand cmd = new SqlCommand(query))
            {
                cmd.Connection = con;
                con.Open();
                using (SqlDataReader sdr = cmd.ExecuteReader())
                {
                    while (sdr.Read())
                    {
                        items.Add(new SelectListItem
                        {
                            Text = sdr["TrackName"].ToString(),
                            Value = sdr["UserId"].ToString()
                        });
                    }
                }
                con.Close();
            }
        }

        return items;
      }
   }
}

HomeIndex Model I have

public class HomeIndex
{
    public TrackModel TrackModel { get; set; }       
}

TrackModel I Have

public class TrackModel
{
    public List<SelectListItem> Tracks { get; set; }
    public int? TrackId { get; set; }
    public int? TrackName { get; set; }
}

My razor view

@using (Html.BeginForm("Index", "Home", FormMethod.Post))
{
    <table>
        <tr>
            <td>
                Tracks:
            </td>
            <td>
                @Html.DropDownListFor(m => m.TrackModel.TrackId, Model.TrackModel.Tracks, "Please select")
            </td>
        </tr>
        <tr>
            <td>
                Track Name:
            </td>
            <td>
                @Html.TextBoxFor(m => m.TrackModel.TrackName)
            </td>
        </tr>
        <tr>
            <td></td>
            <td>
                <input type="submit" value="Submit" />
            </td>
        </tr>
    </table>
}
Grey Walker
  • 125
  • 16
  • @Erik Philips can you link the pages with the answers instead of the profile pages those users have hundreds of questions posted. Thanks – Grey Walker Jul 13 '17 at 23:05
  • I posted nothing. This is a feature of Stack Overflow. The link at the top does **NOT** goto a profile page, it goes to the duplicate question you asked with 27 answers. Here is the same link: [What is a NullReferenceException, and how do I fix it?](https://stackoverflow.com/questions/4660142/what-is-a-nullreferenceexception-and-how-do-i-fix-it) – Erik Philips Jul 14 '17 at 17:13

2 Answers2

0

You are populating your TrackModel then passing a new HomeIndex model to your view without ever assigning your TrackModel to your HomeIndex model in your controller get method.

You are basically passing an empty HomeIndex model to your view.

Also, it may be best to refactor your code so that your trackmodel gets auto populated in your HomeIndex constructor if you call it without any parameters.

Travis Acton
  • 4,292
  • 2
  • 18
  • 30
0

You can easily do this with the code below:

In your Controller Get & Post Action:

Add like this:

ViewBag.GivenName = UrDatabase.DatabaseName;

In View:

You can Use like this:

@Html.DropDownListFor(m => m.TrackModel.TrackId ,
                                new SelectList(ViewBag.GivenName, "requiredValue(like ID or anything from the database)", "requiredView(To show in dropdown should be in database)"),
                                 "Please select", new { @class = "form-control" })
Luqman
  • 139
  • 2
  • 15