I intend to display a list of employees with about five columns on the left side of my razor view, and on selecting any employee (row), display details of the employee as a readonly partial view on the right - as in the image below. My wish is to reuse the details form later in another view to add/update records.
My controller is shown below:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.Web.Mvc;
namespace Mymvc.Controllers
{
public class EmpController : Controller
{
private readonly MyEntities _db = new MyEntities();
private IEnumerable<vEmployee> _Employees;
// GET: Employee
public ActionResult Index()
{
ViewData["ModuleName"] = "Active Employees";
ViewData["deptIDList"] = _db.lu_Department.OrderBy(e => e.Dept);
ViewData["jobTitleIDList"] = _db.lu_JobTitle.OrderBy(e => e.JobTitle);
ViewData["genderList"] = _db.lu_Gender.OrderBy(e => e.Gender);
ViewData["ethnicityList"] = _db.lu_Ethnicity.OrderBy(e => e.Ethnicity);
ViewData["nationalityList"] = _db.lu_Nationality.OrderBy(e => e.Nationality);
ViewData["staffLocationList"] = _db.lu_StaffLocation.OrderBy(e => e.StaffLocation);
ViewData["notchList"] = _db.lu_EmploymentGradeNotch.OrderBy(e => e.Notch);
ViewData["salutationList"] = _db.lu_Salutation.OrderBy(e => e.Title);
return View();
}
public ActionResult EmployeeDetails(int employeeID = 0)
{
vEmployee SelectedEmployee = null;
ViewData["deptIDList"] = _db.lu_Department.OrderBy(e => e.Dept);
ViewData["jobTitleIDList"] = _db.lu_JobTitle.OrderBy(e => e.JobTitle);
ViewData["genderList"] = _db.lu_Gender.OrderBy(e => e.Gender);
ViewData["ethnicityList"] = _db.lu_Ethnicity.OrderBy(e => e.Ethnicity);
ViewData["nationalityList"] = _db.lu_Nationality.OrderBy(e => e.Nationality);
ViewData["staffLocationList"] = _db.lu_StaffLocation.OrderBy(e => e.StaffLocation);
ViewData["notchList"] = _db.lu_EmploymentGradeNotch.OrderBy(e => e.Notch);
ViewData["salutationList"] = _db.lu_Salutation.OrderBy(e => e.Title);
try
{
if (employeeID == 0)
employeeID = _db.Employees.OrderBy(m => m.EmployeeNumber).First().EmployeeID;
if (_Employees == null)
_Employees = GetEmployees();
SelectedEmployee = _Employees.First(e => e.EmployeeID == employeeID);
}
catch (Exception e)
{
var msg = e.Message;
}
return View(SelectedEmployee);
}
private IEnumerable<vEmployee> GetEmployees()
{
IEnumerable<vEmployee> emp = (from e in _db.Employees
join c in _db.Contacts on e.EmployeeID equals c.EmployeeID
join g in _db.lu_EmploymentGradeNotch on e.NotchID equals g.NotchID
join u in _db.lu_Salutation on c.SalutationID equals u.TitleID into sal
from u in sal.DefaultIfEmpty()
join s in _db.lu_SUBDepartment on e.SubDeptID equals s.SubDeptID into sde
from s in sde.DefaultIfEmpty()
join l in _db.lu_StaffLocation on e.StaffLocationID equals l.StaffLocationID into cl
from cm in cl.DefaultIfEmpty()
join t in _db.lu_Ethnicity on c.EthnicityID equals t.EthnicityID into eth
from et in eth.DefaultIfEmpty()
join n in _db.lu_Nationality on c.NationalityID equals n.NationalityID into nt
from nt1 in nt.DefaultIfEmpty()
where c.ContactTypeID == 1 && e.EmploymentStatusID == 1
select new vEmployee
{
EmployeeID = e.EmployeeID,
EmployeeNumber = e.EmployeeNumber,
DeptID = e.DeptID,
SubDeptID = e.SubDeptID,
JobTitleID = e.JobTitleID,
ReportsToID = e.ReportsToID,
NotchID = g.NotchID,
HireDate = e.HireDate,
StaffLocationID = e.StaffLocationID,
FirstName = c.FirstName,
LastName = c.LastName,
MiddleName = c.MiddleName,
FullName = c.FirstName + (c.MiddleName == null ? "" : " " + c.MiddleName) + " " + c.LastName + " (" + u.Title + ")",
SalutationID = c.SalutationID,
GenderID = c.GenderID,
EthnicityID = c.EthnicityID,
NationalityID = c.NationalityID,
Photograph = e.Photograph
})
.AsEnumerable()
.OrderBy(m => m.EmployeeNumber)
.ThenBy(m => m.FirstName);
return emp;
}
public ActionResult ActiveEmployees_Read([DataSourceRequest] DataSourceRequest request)
{
_Employees = GetEmployees();
return Json(_Employees.ToDataSourceResult(request, ModelState), JsonRequestBehavior.AllowGet);
}
}
}
My Main Index view:
#using Mymvc.Models
#model Mymvc.Models.vEmployee
#using System.Collections
<div class="col col-xs-6">
#(Html.Kendo().Grid<vEmployee>()
.Name("EmployeesList")
.Columns(columns =>
{
columns.Bound(p => p.EmployeeNumber).Width(35);
columns.Bound(p => p.FirstName).Width(60);
columns.Bound(p => p.LastName).Width(60);
columns.ForeignKey(p => p.JobTitleID, (IEnumerable)ViewData["jobTitleIDList"], "JobTitleID", "JobTitle")
.Width(60);
columns.ForeignKey(p => p.DeptID, (IEnumerable)ViewData["deptIDList"], "DeptID", "Dept")
.Width(60);
})
.Events(e => e.Change("Grid_OnRowSelect"))
.Events(e => e.DataBound("Grid_OnDataBound"))
.DataSource(dataSource => dataSource
.Ajax()
.PageSize(15)
.ServerOperation(false)
.Events(events => events.Error("grid_error")) // Handle the "error" event
.Model(model =>
{
model.Id(m => m.EmployeeID);
model.Field(m => m.EmployeeID).Editable(false);
})
.Read(read => read.Action("ActiveEmployees_Read", "Employee"))
)
.Filterable()
.Pageable()
.Sortable()
.Selectable()
)
</div>
#Html.Partial("_EmployeeDetails");
<script type="text/javascript">
Grid_OnDataBound = function (e) {
var grid = $("#EmployeesList").data("kendoGrid");
grid.select(e.sender.tbody.find("tr:first"));
}
Grid_OnRowSelect = function (e) {
var data = this.dataItem(this.select());
var empID = data.id;//IMP
$.ajax({
url: '/Employee/EmployeeDetails',
type: "GET",
//dataType: "JSON",
data: { 'employeeID': empID }
});
}
</script>
Upon selecting any employee on my list my OnDataBound and OnRowSelect events send the selected EmployeeID to my EmployeeDetails controller method.
My PartialView:
#model Mymvc.Models.vEmployee
#using System.Collections
<div class="col col-xs-6">
#using (Html.BeginForm("EmployeeDetails", "Employee"))
{
<div class="container">
<div class="col-md-8 well">
<div class="form-horizontal">
#Html.ValidationSummary(true, "", new { #class = "text-danger" })
<div id="updateMsg" class="demo-section k-content"></div>
<div class="form-group">
#Html.LabelFor(model => model.LastName, htmlAttributes: new { #class = "control-label col-md-3" })
<div class="col-md-5">
#Html.TextBoxFor(model => model.LastName, new { style = "width: 400px" })
#Html.ValidationMessageFor(model => model.LastName, "", new { #class = "text-danger" })
</div>
</div>
<div class="form-group">
#Html.LabelFor(model => model.FirstName, htmlAttributes: new { #class = "control-label col-md-3" })
<div class="col-md-5">
#Html.TextBoxFor(model => model.FirstName, new { style = "width: 400px" })
#Html.ValidationMessageFor(model => model.FirstName, "", new { #class = "text-danger" })
</div>
</div>
<div class="form-group">
#Html.LabelFor(model => model.MiddleName, htmlAttributes: new { #class = "control-label col-md-3" })
<div class="col-md-5">
#Html.TextBoxFor(model => model.MiddleName, new { style = "width: 400px" })
#Html.ValidationMessageFor(model => model.MiddleName, "", new { #class = "text-danger" })
</div>
</div>
<div class="form-group">
#Html.LabelFor(model => model.SalutationID, htmlAttributes: new { #class = "control-label col-md-3" })
<div class="col-md-2">
#Html.DropDownListFor(model => model.SalutationID, new SelectList((IEnumerable)ViewData["salutationList"], "TitleID", "Title"))
#Html.ValidationMessageFor(model => model.SalutationID, "", new { #class = "text-danger" })
</div>
#Html.LabelFor(model => model.GenderID, htmlAttributes: new { #class = "control-label col-md-2 col-md-offset-2" })
<div class="col-md-1">
#Html.DropDownListFor(model => model.GenderID, new SelectList((IEnumerable)ViewData["genderList"], "GenderID", "Gender"))
#Html.ValidationMessageFor(model => model.GenderID, "", new { #class = "text-danger" })
</div>
</div>
<div class="form-group">
#Html.LabelFor(model => model.NationalityID, htmlAttributes: new { #class = "control-label col-md-3" })
<div class="col-md-1">
#Html.DropDownListFor(model => model.NationalityID, new SelectList((IEnumerable)ViewData["nationalityList"], "NationalityID", "Nationality"))
#Html.ValidationMessageFor(model => model.NationalityID, "", new { #class = "text-danger" })
</div>
</div>
<div class="form-group">
#Html.LabelFor(model => model.EthnicityID, htmlAttributes: new { #class = "control-label col-md-3" })
<div class="col-md-1">
#Html.DropDownListFor(model => model.EthnicityID, new SelectList((IEnumerable)ViewData["ethnicityList"], "EthnicityID", "Ethnicity"))
#Html.ValidationMessageFor(model => model.EthnicityID, "", new { #class = "text-danger" })
</div>
</div>
<div class="form-group">
#Html.LabelFor(model => model.Photograph, htmlAttributes: new { #class = "control-label col-md-3" })
<div class="col-md-5">
#Html.TextBoxFor(model => model.Photograph, new { style = "width: 180px" })
#Html.ValidationMessageFor(model => model.Photograph, "", new { #class = "text-danger" })
</div>
</div>
</div>
<style>
.demo-section {
text-align: center;
line-height: 4em;
}
</style>
</div>
</div>
}
</div>
My Challenge:
I cannot populate my details partialview with model information on selecting an employee on the left list. When I view the SelectedEmployee object in the EmployeeDetails method in debug, the details (lastname, firstname, etc.) can be seen confirming my ajax method is working well.
What am I doing wrong here? Also, is there a better method of presenting list and detail in the same view in mvc?
Thanks!
#Html.Partial("_EmployeeDetails") only call _EmployeeDetails view. This code cannot call Controller _EmployeeDetails method.
So, as you need , Access the view through the controller
Change #Html.Partial("_EmployeeDetails") to #Html.Action("_EmployeeDetails");
_EmployeeDetails action can be take selected Id parameter.
#Html.Action("_EmployeeDetails", new { id = yourSelectedRowIdValue })
You can find the selected id and return from the _EmployeeDetails method spesific detail data.
public ActionResult _EmployeeDetails (int id)
{
// var employeeDetail = find _EmployeeDetail using by id
return View (employeeDetail );
}
Related
In my views, I have a few drop-down lists that I use to get the ID and show the value to the user so they know what they are choosing. But in the view that I use to list everything that has already been added, it shows the chosen ID, but I want the name to appear
I tried this but it always shows the status that has the ID 1, which is the status "Active"
#Html.DropDownListFor(modelItem => item.status,
(SelectList)ViewBag.listStatus,
new { #class disabled = "" })
//controller
{
public ActionResult listStatus()
{
var list= ListsDAO.listStatus();
return View(list);
}
}
//DAO
{
public static IEnumerable<LISTS> listStatus()
{
using (var ctx = new PadraoEntities())
{
var result= from lists in ctx.LISTS
where lists.TYPE_LIST== "STATUS"
select new
{
lists.IDE_LIST,
lists.DES_LIST,
lists.VLR_LIST
};
var list= new List<LISTS>();
foreach (var item in result)
{
list.Add(new LISTS()
{
IDE_LIST = item.IDE_LIST,
VLR_LIST = item.VLR_LIST,
DES_LIST = item.DES_LIST
});
}
return list;
}
}
}
//view add
<div class="form-group">
#Html.LabelFor(model => model.status, htmlAttributes: new { #class = "control -Label col-md-2" })
<div class="col-md-10">
#Html.DropDownListFor(model => model.status(SelectList)ViewBag.listStatus, new { #class = "form-control" })
#Html.ValidationMessageFor(model => model.status, "", new { #class = "text-danger" })
</div>
</div>
//view list
{
#Html.DropDownListFor(modelItem => item.ststus,(SelectList)ViewBag.listStatus,new { disabled = "" })
}
when listing id 1, I expected "active" to appear, id 2 shows "inactive", etc
Try this //controller
public ActionResult listStatus()
{
ViewBag.Status = new SelectList(//Code to get id and its property, "StatusId", "Status");
var list= ListsDAO.listStatus();
return View(list);
}
//View
<div class="form-group">
#Html.LabelFor(model => model.Status, "TaskId", htmlAttributes: new { #class = "control-label col-md-2" })
<div class="col-md-10">
#Html.DropDownList("Status", null, htmlAttributes: new { #class = "form-control" })
#Html.ValidationMessageFor(model => model.Status, "", new { #class = "text-danger" })
</div>
</div>
Having a problem returning and passing the desired values to the View. I run the LINQ query in LINQPad4 and it returns the correct results. I feel I'm missing something simple here. I've using this post HERE as a reference
Im getting the
CS1061: 'IEnumerable' does not contain a definition for 'FirstName' and no extension method 'FirstName' accepting a first argument of type 'IEnumerable' could be found (are you missing a using directive or an assembly reference?)ERROR.
\
When I run and step through the code i dont see any values and the message I'm given is
Message = "Unable to create a constant value of type 'System.Object'. Only primitive types or enumeration types are supported in this context."
UPDATE
Changing the View from #model IEnumerable<Login.Models.EditProfile> to #model Login.Models.EditProfile Helped with the CS1061 Error I was having and as for the LINQ query not working please look at the accepted answer below by Titian.
Any help would be greatly appreciated.
Let me know If there is more information I can provide.
/ Controller /
public ActionResult Edit(int? id)
{
using (TDBEntities db1 = new TDBEntities())
{
var user = (from a in db1.ExternalUsers
join b in db1.ExternalUserEmails on a.ExternalUserID equals b.ExternalUserID
join c in db1.ExternalUserPhones on a.ExternalUserID equals c.ExternalUserID
where a.ExternalUserID.Equals(id)
select new EditProfile {ExternalUserID = a.ExternalUserID, FirstName = a.FirstName, LastName = a.LastName, EmailAddress = b.EmailAddress, PhoneNumber = c.PhoneNumber });
if (user == null)
{
return HttpNotFound();
}
return View(user);
}
}
/Model/
public partial class EditProfile
{
public string FirstName { get; set; }
public string LastName { get; set; }
public string EmailAddress { get; set; }
public string PhoneNumber { get; set; }
public int ExternalUserID { get; set; }
}
/View/
#model IEnumerable<Login.Models.EditProfile>
#using Login.Helpers
#{
ViewBag.Title = "Update Employee";
}
<h2></h2>
#using (Html.BeginForm())
{
#Html.AntiForgeryToken()
<div class="form-horizontal">
<h4>Update Employee</h4>
<hr />
<div class="form-group">
#Html.LabelFor(model => model.FirstName, "First Name:", htmlAttributes: new { #class = "control-label col-md-2" })
<div class="col-md-10">
#Html.EditorFor(model => model.FirstName, new { htmlAttributes = new { #class = "form-control" } })
#Html.ValidationMessageFor(model => model.FirstName, "", new { #class = "text-danger" })
</div>
</div>
<div class="form-group">
#Html.LabelFor(model => model.LastName, "Last Name:", htmlAttributes: new { #class = "control-label col-md-2" })
<div class="col-md-10">
#Html.EditorFor(model => model.LastName, new { htmlAttributes = new { #class = "form-control" } })
#Html.ValidationMessageFor(model => model.LastName, "", new { #class = "text-danger" })
</div>
</div>
<div class="form-group">
#Html.LabelFor(model => model.EmailAddress, "Email Address:", htmlAttributes: new { #class = "control-label col-md-2" })
<div class="col-md-10">
#Html.EditorFor(model => model.EmailAddress, new { htmlAttributes = new { #class = "form-control" } })
#Html.ValidationMessageFor(model => model.EmailAddress, "", new { #class = "text-danger" })
</div>
</div>
<div class="form-group">
#Html.LabelFor(model => model.PhoneNumber, "Phone Number:", htmlAttributes: new { #class = "control-label col-md-2" })
<div class="col-md-10">
#Html.EditorFor(model => model.PhoneNumber, new { htmlAttributes = new { #class = "form-control" } })
#Html.ValidationMessageFor(model => model.PhoneNumber, "", new { #class = "text-danger" })
</div>
</div>
<div class="form-group">
<label class="resetPw control-label col-md-2 ">Reset Password</label>
<div> #Html.CheckBox("ResetPassword", false, new { #style = "margin: 10px 15px 0;" }) <i>(check to reset)</i></div>
</div>
<div class="form-group">
<div class="col-md-offset-2 col-md-10">
<input type="submit" value="Save" class="btn btn-default" />
</div>
</div>
</div>
}
<div>
#Html.ActionLink("Back to List", "Index")
You want to add a FirstOrDefault to your query. Select will return a value (of type IQueryable<User>) even if there are no values (an empty result). You actually want the first value in that result or null if there are no matching results:
var user = (from a in db1.ExternalUsers
join b in db1.ExternalUserEmails on a.ExternalUserID equals b.ExternalUserID
join c in db1.ExternalUserPhones on a.ExternalUserID equals c.ExternalUserID
where a.ExternalUserID == id
select new EditProfile {ExternalUserID = a.ExternalUserID, FirstName = a.FirstName, LastName = a.LastName, EmailAddress = b.EmailAddress, PhoneNumber = c.PhoneNumber })
.FirstOrDefault();
I know that the question was asked and answered many times, but unfortunately no one of the answers helped me.
I have tree POCO models, which are Pharmacy, Address and Company gathered together into a ViewModel PharmacyVM:
public class PharmacyVM
{
public Pharmacy pharmacyProp { get; set; }
public Address addressProp { get; set; }
public Company companyProp { get; set; }
public int CityId { get; set; }
public PharmacyVM()
{
pharmacyProp = new Pharmacy();
addressProp = new Address();
companyProp = new Company();
}
}
Don't laugh at the properties names; at the start, they had been normal (Address, Company and Pharmacy) I changed them according to one of the lots of answers in here, but... it didn't help :(
In the Get action of the Create method I'm trying to manually create the PharmacyVM object and pass it to the view:
public ActionResult Create()
{
ViewBag.CityId = new SelectList(db.Cities, "Id", "Name");
ViewBag.CompanyId = new SelectList(db.Companies, "Id", "Name");
ViewBag.AddressId = new SelectList(db.Addresses, "Id", "Name");
ViewBag.CityId = new SelectList(db.Cities, "Id", "Name");
ViewBag.RegionId = new SelectList(db.Regions, "Id", "Name");
ViewBag.DistrictId = new SelectList(db.Districts, "Id", "Name");
ViewBag.MicrodistrictId = new SelectList(db.Microdistricts, "Id", "Name");
ViewBag.StreetId = new SelectList(db.Streets, "Id", "Name");
ViewBag.VillageId = new SelectList(db.Villages, "Id", "Name");
var pharmacyVM = new PharmacyVM();
return View(pharmacyVM);
}
There is a standard Razor code in the view:
#model MEDONET.Models.PharmacyVM
#{
ViewBag.Title = "Create";
}
<h2>Create</h2>
#using (Html.BeginForm("Create", "Pharmacies", FormMethod.Post, new { enctype = "multipart/form-data" }))
{
#Html.AntiForgeryToken()
<div class="form-horizontal">
<h4>pharmacyProp</h4>
<hr />
#Html.ValidationSummary(true, "", new { #class = "text-danger" })
<div class="form-group">
#Html.LabelFor(model => model.companyProp, htmlAttributes: new { #class = "control-label col-md-2" })
<div class="col-md-10">
#Html.DropDownList("CompanyId", null, "", htmlAttributes: new { #class = "form-control" })
#Html.ValidationMessageFor(model => model.companyProp.Id, "", new { #class = "text-danger" })
</div>
</div>
<div class="form-group">
#Html.LabelFor(model => model.pharmacyProp.Name, htmlAttributes: new { #class = "control-label col-md-2" })
<div class="col-md-10">
#Html.EditorFor(model => model.pharmacyProp.Name, new { htmlAttributes = new { #class = "form-control" } })
#Html.ValidationMessageFor(model => model.pharmacyProp.Name, "", new { #class = "text-danger" })
</div>
</div>
<div class="form-group">
#Html.LabelFor(model => model.addressProp.City, htmlAttributes: new { #class = "control-label col-md-2" })
<div class="col-md-10">
#Html.DropDownList("CityId", null, "", htmlAttributes: new { #class = "form-control" })
#Html.ValidationMessageFor(model => model.CityId, "", new { #class = "text-danger" })
</div>
</div>
<div class="form-group">
#Html.LabelFor(model => model.CityId, htmlAttributes: new { #class = "control-label col-md-2" })
<div class="col-md-10">
#Html.DropDownList("CityId", null, "", htmlAttributes: new { #class = "form-control" })
#Html.ValidationMessageFor(model => model.CityId, "", new { #class = "text-danger" })
</div>
</div>
<div class="form-group">
#Html.LabelFor(model => model.addressProp.Village, htmlAttributes: new { #class = "control-label col-md-2" })
<div class="col-md-10">
#Html.DropDownList("VillageId", null, "", htmlAttributes: new { #class = "form-control" })
#Html.ValidationMessageFor(model => model.addressProp.VillageId, "", new { #class = "text-danger" })
</div>
</div>
<div class="form-group">
#Html.LabelFor(model => model.addressProp.District, htmlAttributes: new { #class = "control-label col-md-2" })
<div class="col-md-10">
#Html.DropDownList("DistrictId", null, "", htmlAttributes: new { #class = "form-control" })
#Html.ValidationMessageFor(model => model.addressProp.DistrictId, "", new { #class = "text-danger" })
</div>
</div>
<div class="form-group">
#Html.HiddenFor(model => model.addressProp.RegionId)
#Html.LabelFor(model => model.addressProp.Region, htmlAttributes: new { #class = "control-label col-md-2" })
<div class="col-md-10">
#Html.DropDownList("RegionId", null, "", htmlAttributes: new { #class = "form-control" })
#Html.ValidationMessageFor(model => model.addressProp.RegionId, "", new { #class = "text-danger" })
</div>
</div>
<div class="form-group">
#Html.LabelFor(model => model.addressProp.Microdistrict, htmlAttributes: new { #class = "control-label col-md-2" })
<div class="col-md-10">
#Html.DropDownList("MicrodistrictId", null, "", htmlAttributes: new { #class = "form-control" })
#Html.ValidationMessageFor(model => model.addressProp.MicrodistrictId, "", new { #class = "text-danger" })
</div>
</div>
<div class="form-group">
#Html.LabelFor(model => model.addressProp.Building, htmlAttributes: new { #class = "control-label col-md-2" })
<div class="col-md-10">
#Html.EditorFor(model => model.addressProp.Building, new { htmlAttributes = new { #class = "form-control" } })
#Html.ValidationMessageFor(model => model.addressProp.Building, "", new { #class = "text-danger" })
</div>
</div>
<div class="form-group">
#Html.LabelFor(model => model.addressProp.Street, htmlAttributes: new { #class = "control-label col-md-2" })
<div class="col-md-10">
#Html.DropDownList("MicrodistrictId", null, "", htmlAttributes: new { #class = "form-control" })
#Html.ValidationMessageFor(model => model.addressProp.MicrodistrictId, "", new { #class = "text-danger" })
</div>
</div>
<div class="form-group">
#Html.LabelFor(model => model.pharmacyProp.IsGov, htmlAttributes: new { #class = "control-label col-md-2" })
<div class="col-md-10">
<div class="checkbox">
#Html.EditorFor(model => model.pharmacyProp.IsGov)
#Html.ValidationMessageFor(model => model.pharmacyProp.IsGov, "", new { #class = "text-danger" })
</div>
</div>
</div>
<div class="form-group">
#Html.LabelFor(model => model.companyProp, htmlAttributes: new { #class = "control-label col-md-2" })
<div class="col-md-10">
#Html.DropDownList("companyId", null, "", htmlAttributes: new { #class = "form-control" })
#Html.ValidationMessageFor(model => model.pharmacyProp.CompanyId, "", new { #class = "text-danger" })
</div>
</div>
<div class="form-group">
#Html.LabelFor(model => model.pharmacyProp.LargeImage, htmlAttributes: new { #class = "control-label col-md-2" })
<div class="col-md-10">
<input type="file" name="LargeImageFile" required />
</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>
#section Scripts {
#Scripts.Render("~/bundles/jqueryval")
}
And then in the Post action of the Create method, I'm trying to create b and c variables:
[HttpPost]
[ValidateAntiForgeryToken]
public ActionResult Create(PharmacyVM model, HttpPostedFileBase LargeImageFile)
{
if (ModelState.IsValid)
{
string LargeImageFileName = Path.GetFileNameWithoutExtension(LargeImageFile.FileName);
string LargeImageExtansion = Path.GetExtension(LargeImageFile.FileName);
LargeImageFileName = LargeImageFileName + DateTime.Now.ToString("yymmssfff") + LargeImageExtansion;
LargeImageFileName = Path.Combine(Server.MapPath("~/Images/Pharmacy/Banners/"), LargeImageFileName);
int b = model.CityId;
int c = model.addressProp.RegionId.Value;
//Address address = new Address()
//{
// Id = 12,//db.Addresses.AsEnumerable().Last().Id + 1,
// RegionId = PharmacyVM.Address.RegionId,
// DistrictId = PharmacyVM.Address.DistrictId,
// CityId = PharmacyVM.Address.CityId,
// MicrodistrictId = PharmacyVM.Address.MicrodistrictId,
// StreetId = PharmacyVM.Address.StreetId,
// VillageId = PharmacyVM.Address.VillageId,
// Building = PharmacyVM.Address.Building,
// Cab = PharmacyVM.Address.Cab
//};
//Address address = new Address
//{
// Id = 12,//db.Addresses.AsEnumerable().Last().Id + 1,
// RegionId = 1,
// DistrictId = 1,
// CityId = 1,
// MicrodistrictId = 1,
// StreetId = 1,
// VillageId = 1,
// Building = "1",
// Cab = "1"
//};
//db.Addresses.Add(address);
db.SaveChanges();
var pharmacy = new Pharmacy
{
Name = model.pharmacyProp.Name,
//AddressId = address.Id,
IsGov = model.pharmacyProp.IsGov,
CompanyId = model.pharmacyProp.CompanyId,
LargeImage = "~/Images/Pharmacy/Banners/" + LargeImageFileName
};
LargeImageFile.SaveAs(LargeImageFileName);
db.Pharmacies.Add(pharmacy);
db.SaveChanges();
ModelState.Clear();
return RedirectToAction("Index");
}
}
Unlike first variable b, the second one c is gonna be null because the addressProp property is null.
So why is it so strange? How can I use ViewModel without duplicating original model's fields?
why are you use
int b= model.addressProp.RegionId.Value
instead of
int b=model.addressProp.RegionId
Even for your good cording the best and good way is remove all View bag and
Add all View bag properties to PharmacyVM Class
Dont use two properties for view binding
Example
public class PharmacyVM
{
public Pharmacy pharmacyProp { get; set; }
public Address addressProp { get; set; }
public Company companyProp { get; set; }
public int CityId { get; set; }
public SelectList CityIdList { get; set; }
public PharmacyVM()
{
pharmacyProp = new Pharmacy();
addressProp = new Address();
companyProp = new Company();
CityIdList =new SelectList(db.Cities, "Id", "Name");
}
}
public ActionResult Create()
{
var pharmacyVM = new PharmacyVM();
return View(pharmacyVM);
}
#model PharmacyVM
#using (Html.BeginForm())
{
#Html.HiddenFor(m => m.CityId )
<div class="editor-label">
#Html.LabelFor(m => m.Name)
</div>
<div class="editor-field">
#Html.EditorFor(m => m.Name)
#Html.ValidationMessageFor(m => m.Name)
</div>
<button type="submit">Create</button>
}
[HttpPost]
public ActionResult Create(PharmacyVM model)
{
int c = model.addressProp
return View(viewModel);
}
More Information
I have feedback form with two fields : project_name and lastName of partner. The first fiels is correct(project_name) but instead lastName of second field I want there firstName+lastName+email, how to do it? At the moment there is only lastname, but I can have multiply lastnames for different partners. Below is sample of code how I create this form.
In my create method of feedbackController:
ViewBag.project_id = new SelectList(db.Projects.Where(p => p.project_id == project_id), "project_id", "name");
ViewBag.Id = new SelectList(db.Users_projects.Where(p => p.project_id == project_id && p.project_role == "partner").Select(up => new { up.AspNetUsers.FirstName,up.AspNetUsers.LastName, up.AspNetUsers.Id }), "Id", "LastName");
Here is my view how render this form:
<div class="form-horizontal">
<h4></h4>
<hr />
#Html.ValidationSummary(true, "", new { #class = "text-danger" })
<div class="form-group">
#Html.LabelFor(model => model.project_id, "Project: ", htmlAttributes: new { #class = "control-label col-md-2" })
<div class="col-md-10">
#Html.DropDownList("project_id", null, htmlAttributes: new { #class = "form-control" })
#Html.ValidationMessageFor(model => model.project_id, "", new { #class = "text-danger" })
</div>
</div>
<div class="form-group">
#Html.LabelFor(model => model.Id, " For partner : ", htmlAttributes: new { #class = "control-label col-md-2" })
<div class="col-md-10">
#Html.DropDownList("Id", null, htmlAttributes: new { #class = "form-control" })
#Html.ValidationMessageFor(model => model.Id, "", new { #class = "text-danger" })
</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>
ViewBag.Id =db.Users_projects
.Where(p => p.project_id == project_id &&p.project_role == "partner")
.Select(up =>
new SelectListItem {
// You may append User email also here
Text= up.AspNetUsers.FirstName +" "+up.AspNetUsers.LastName,
Value = up.AspNetUsers.Id.ToString() })
.ToList();
You can make your code more readable/maintainable by not using dynamic stuff like ViewBag and switch to a strongly typed viewmodel to pass the data between your action method and view
public class AssignProjectOwnerShipVm
{
public int SelectedPartner {set;get;}
public int SelectedProject {set;get;}
public List<SelectListItem> Projects {set;get;}
public List<SelectListItem> Partners {set;get;}
}
and in your GET action
pubilc ActionResult AssignProject()
{
var vm = new AssignProjectOwnerShipVm();
vm.Projects = db.Projects.Select(s=>new SelectListItem
{
Value = s.ProjectId.ToString(),
Text = s.ProjectName
}).ToList();
vm.Partners=db.Users_projects
.Where(p => p.project_id == project_id &&p.project_role == "partner")
.Select(up =>
new SelectListItem {
// You may append User email also here
Text= up.AspNetUsers.FirstName +" "+up.AspNetUsers.LastName,
Value = up.AspNetUsers.Id.ToString() })
.ToList();
return View(vm);
}
And your view
#model AssignProjectOwnerShipVm
#using(Html.BeginForm())
{
#Html.DrowpDownListFor(s=>s.SelectedProject,Model.Projects,"Select one")
#Html.DrowpDownListFor(s=>s.SelectedPartner,Model.Partners,"Select one")
<input type="submit" />
}
And your HttpPost
[HttpPost]
public ActionResult AssignProjecct(AssignProjectOWnerShipVm model)
{
// check for model.SelectedParter and model.SelectedProject
// to do :Save and redirect
}
As the title says, I'am trying to write an algoritm with these conditions:
Each employee has a flextime balance which is initially zero.
If the total time of all stamp ins and stamp outs in a working day exceeds 8 hours, the flexitime balance listed with the prolonged time , and the same principle applies to the deficit.
Flextime balance is listed with all the time stamped on the days that are relieved of work.
If no stamps occurred on a working day then the flextime balance is not affected.
There are two tables im having in the database: NonWorkingDays and Stampings.
NonWorkingDays contains only of one column which is: "Days (DateTime)".
Stampings contains of four columns: "Id (Int) (PK), UserId (Int), Timestamp (DateTime), StampingType (value "in" and value "out")
This is what I wrote so far -
Model:
public class FlexModel
{
public List<User> Users { get; set; }
public List<Stamping> Stampings { get; set; }
public decimal FlexTime { get; set; }
}
View:
#model Aviato.ViewModel.FlexModel
#{
Layout = "~/Views/Shared/_Layout.cshtml";
}
#using (Html.BeginForm())
{
#Html.AntiForgeryToken()
<div class="form-horizontal">
<h2>Info</h2>
<hr />
#Html.ValidationSummary(true, "", new { #class = "text-danger" })
#Html.HiddenFor(model => model.Users[0].UserId)
#Html.HiddenFor(model => model.Users[0].SocialSecurityNumber)
#Html.HiddenFor(model => model.Users[0].FirstName)
#Html.HiddenFor(model => model.Users[0].LastName)
#Html.HiddenFor(model => model.Users[0].EmploymentStartDate)
#Html.HiddenFor(model => model.Users[0].EmploymentEndDate)
#Html.HiddenFor(model => model.Users[0].Password)
#Html.HiddenFor(model => model.Users[0].RoleName)
<div class="form-group">
#Html.LabelFor(model => model.Users[0].Address1, htmlAttributes: new { #class = "control-label col-md-2" })
<div class="col-md-10">
#Html.EditorFor(model => model.Users[0].Address1, new { htmlAttributes = new { #class = "form-control" } })
#Html.ValidationMessageFor(model => model.Users[0].Address1, "", new { #class = "text-danger" })
</div>
</div>
<div class="form-group">
#Html.LabelFor(model => model.Users[0].Address2, htmlAttributes: new { #class = "control-label col-md-2" })
<div class="col-md-10">
#Html.EditorFor(model => model.Users[0].Address2, new { htmlAttributes = new { #class = "form-control" } })
#Html.ValidationMessageFor(model => model.Users[0].Address2, "", new { #class = "text-danger" })
</div>
</div>
<div class="form-group">
#Html.LabelFor(model => model.Users[0].ZipCode, htmlAttributes: new { #class = "control-label col-md-2" })
<div class="col-md-10">
#Html.EditorFor(model => model.Users[0].ZipCode, new { htmlAttributes = new { #class = "form-control" } })
#Html.ValidationMessageFor(model => model.Users[0].ZipCode, "", new { #class = "text-danger" })
</div>
</div>
<div class="form-group">
#Html.LabelFor(model => model.Users[0].City, htmlAttributes: new { #class = "control-label col-md-2" })
<div class="col-md-10">
#Html.EditorFor(model => model.Users[0].City, new { htmlAttributes = new { #class = "form-control" } })
#Html.ValidationMessageFor(model => model.Users[0].City, "", new { #class = "text-danger" })
</div>
</div>
<div class="form-group">
#Html.LabelFor(model => model.Users[0].PhoneNumber1, htmlAttributes: new { #class = "control-label col-md-2" })
<div class="col-md-10">
#Html.EditorFor(model => model.Users[0].PhoneNumber1, new { htmlAttributes = new { #class = "form-control" } })
#Html.ValidationMessageFor(model => model.Users[0].PhoneNumber1, "", new { #class = "text-danger" })
</div>
</div>
<div class="form-group">
#Html.LabelFor(model => model.Users[0].PhoneNumber2, htmlAttributes: new { #class = "control-label col-md-2" })
<div class="col-md-10">
#Html.EditorFor(model => model.Users[0].PhoneNumber2, new { htmlAttributes = new { #class = "form-control" } })
#Html.ValidationMessageFor(model => model.Users[0].PhoneNumber2, "", new { #class = "text-danger" })
</div>
</div>
<div class="form-group">
#Html.LabelFor(model => model.FlexTime, htmlAttributes: new { #class = "control-label col-md-2" })
<div class="col-md-10">
#Html.DisplayFor(model => model.FlexTime, new { htmlAttributes = new { #class = "form-control" } })
#Html.ValidationMessageFor(model => model.FlexTime, "", new { #class = "text-danger" })
</div>
</div>
<div class="form-group">
<div class="col-md-offset-2 col-md-10">
<input type="submit" value="Spara" class="btn btn-default" />
</div>
</div>
</div>
}
Controller:
public ActionResult Info()
{
var flexModel = new FlexModel();
var userId = (int)Session["userId"];
var user = _db.Users.Find(userId);
var stampIn = _db.Stampings.Where(i => i.StampingType == "in").Where(i => i.User == user).ToList();
var stampOut = _db.Stampings.Where(i => i.StampingType == "out").Where(i => i.User == user).ToList();
var workDay = 8;
if (stampIn.Count == 0)
{
return View();
}
foreach (var itemIn in stampIn)
{
}
foreach (var itemOut in stampOut)
{
}
return View();
}
[HttpPost]
public ActionResult Info(FlexModel model)
{
if (ModelState.IsValid)
{
foreach (var item in model.Users)
{
_db.Entry(item).State = EntityState.Modified;
}
_db.SaveChanges();
return RedirectToAction("Index");
}
return View(model);
}
So this is not working for me, I get the value of Flex to display 0.
Help would be appreciated!