テキストフィールドが2つ以上のテキスト列で構成される選択リストをどのように生成しますか。たとえば、データベースにDescriptionフィールドとRateフィールドがある場合、これらを組み合わせて表示します。
Large--£200
Medium--£150
Small--£100
コントローラコードは次のとおりです。
var stands = db.Stands.Where(s => s.ExhibitorID == null).ToList();
ViewBag.StandID = new SelectList(stands,"StandID", "Description" + "-- £" + "Rate");
...そして私の見解は(現在):
<div class="editor-field">
@Html.DropDownList("StandID", "--Select--")
</div>
...ただし、「説明」+「-£」+「レート」);実行されません:
DataBinding:「System.Data.Entity.DynamicProxies.Stand_63F8C9F623B3C0E57D3008A57081AFCD9C39E1A6B79B0380B60840F1EFAE9DB4」には「Description--£Rate」という名前のプロパティが含まれていません。
助けてくれてありがとう、
マーク
単純なLINQプロジェクションを使用して新しい匿名クラスを作成し、SelectList(IEnumerable, string, string)
constructor overload を使用して、<option>
に使用する値とテキストフィールドを指定できます。要素すなわち:
var stands =
db.Stands
.Where(s => s.ExhibitorID == null)
.Select(s => new
{
StandID = s.StandID,
Description = string.Format("{0}-- £{1}", s.Description, s.Rate)
})
.ToList();
ViewBag.StandID = new SelectList(stands, "StandID", "Description")
編集
C#6以降では、 文字列補間 はstring.Format
よりも読みやすくなります
...
Description = $"{s.Description}-- £{s.Rate}"
(匿名クラスではなく)強力なViewModel
クラス名に投影する場合、魔法の文字列を nameof
の安全性で置き換えることは間違いないでしょう。オペレーター:
ViewBag.StandID = new SelectList(stands, nameof(Stand.StandID), nameof(Stand.Description));
var stands = db.Stands.Where(s => s.ExhibitorID == null).ToList();
IEnumerable<SelectListItem> selectList = from s in stands
select new SelectListItem
{
Value = s.StandID,
Text = s.Description + "-- £" + s.Rate.ToString()
};
ViewBag.StandID = new SelectList(selectList, "Value", "Text");
部分的なModelクラスを作成できます
public partial class Stand
{
public string DisplayName
{
get
{
return this.Description + "-- £" + this.Rate.ToString();
}
}
}
次に、あなたのビューで
var stands = db.Stands.Where(s => s.ExhibitorID == null).ToList();
ViewBag.StandID = new SelectList(stands,"StandID", "DisplayName");
使用しているコンストラクターの形式はSelectList(IEnumerable items、string dataValueField、string dataTextField)です。
したがって、あなたが持っている方法でそれを使用すると、実際に「Description--£Rate」と呼ばれるTextFieldにバインドするように指示しており、これがDBからのフィールドの呼び出しとは異なる場合、示しています。
上記の2つの方法のいずれかは、dataValueFieldにある値がValueを入れるプロパティの名前と一致し、dataTextFieldがTextを置く場所のプロパティ名と一致する限り機能します。上記のソリューション。 (linqよりもラムダ式の方が好きだからです)。また、selectlist項目を使用すると、変換後にコレクションでToListを実行する必要がなくなります。実際には、選択リストに自然にバインドするオブジェクトを作成しています。
また、説明またはレートをチェックして、リストに入れる前に空でないことを確認することもできます。
var stands = db.Stands.Where(s => s.ExhibitorID == null)
.Select(s => new SelectListItem
{
Value = s.StandID.ToString(),
Text = s.Description + "-- £" + s.Rate.ToString()
});
ViewBag.StandID = new SelectList(stands, "Value", "Text");
ビューモデルを変更してこれを行いました。コードは次のとおりです。
ビューモデル
using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using MvcEsosNew.Models;
using System.Web.Mvc;
namespace MvcEsosNew.ViewModels
{
public class EntitlementViewModel
{
public int EntitlementCount { get; set; }
public Entitlement Entitlement { get; set; }
public SelectList Member { get; set; }
public SelectList Job_Grade { get; set; }
public SelectList Department { get; set; }
public SelectList Esos_Batch { get; set; }
}
public class department_FullName
{
public int deptID { get; set; }
public string deptCode { get; set; }
public string deptName { get; set; }
public string fullName { get { return deptCode + " - " + deptName; } }
}
}
コントローラー
public void getAllDepartment(EntitlementViewModel entitlementVM)
{
var department = from Department in db.Departments.Where(D => D.Status == "ACTIVE").ToList()
select new department_FullName
{
deptID = Department.id,
deptCode = Department.department_code,
deptName = Department.department_name
};
entitlementVM.Department = new SelectList(department, "deptID", "fullName");
}
景色
<div class="form-group row">
<div class="col-sm-2">
@Html.LabelFor(model => model.Entitlement.department_id)
</div>
<div class="col-sm-10">
@Html.DropDownListFor(model => model.Entitlement.department_id, Model.Department, new { @class="form-control" })
@Html.ValidationMessageFor(model => model.Entitlement.department_id)
</div>
</div>
結果: