I have a table called "Tabel_Items" in database with these fields: id, parent, and child:
I want to generate html tags such as these:
<ul>
<li>parent1
<ul>
<li>child1</li>
<li>child2
<ul>
<li>child21</li>
<li>child22</li>
</ul>
</li>
</ul>
</li>
<li>parent2
<ul>
<li>child3</li>
</ul>
</li>
</ul>
I get my items with a LINQ query and pass them to view:
public ActionResult Index()
{
DataClasses1DataContext db = new DataClasses1DataContext();
var items = from i in db.Table_Items
select i;
return View(items);
}
How can I loop through the "items" in view and make a Tree list out of them?
I want a lambda expression to select those rows that have "parentId==null" at first. I test a code like this, but has an error:
#foreach (var i in Model)
{
#Html.DisplayFor(x => i.ItemName.Where(i.ParentId==null));
}
I solved my problem.Thank for me:
<ul>
#foreach (var x in Model.Where(f => f.ParentId == null))
{
<li>
#Html.DisplayFor(f => x.ItemName)
<ul>
#foreach (var y in Model.Where(c => c.ParentId == x.Id))
{
<li>
#Html.DisplayFor(c => y.ItemName)
<ul>
#foreach (var z in Model.Where(c => c.ParentId == y.Id))
{
<li>#Html.DisplayFor(c => z.ItemName)</li>
}
</ul>
</li>
}
</ul>
</li>
}
</ul>
Related
i am using asp.net MVC 5 and Visual studio 2013
and working on Razor view
the view is working fine without if statement around the < li > start
if i enclosed any < li > start, with an if condition statement i get this error
Parser Error Message: Encountered end tag "li" with no matching start tag. Are your start/end tags properly balanced?
#using TheodorHR_App.Models
<div id="tree_CadreGroupLevel" class="tree-demo">
<ul>
#{
TheodorHrEntities db = new TheodorHrEntities();
var nodes = db.Cadres.ToList();
foreach (var node in nodes)
{
Cadre root = new Cadre();
root.Id = node.Id;
if (#Model.RuleElementCadres.Select(e => e).Where(e => e.Cadre == node.Id).Count() > 0)
{
<text>
<li id="Cnode_#node.Id" data-jstree='{ "selected" : true }'>
</text>
}
else
{
<text>
<li id="Cnode_#node.Id">
</text>
}
#node.Name
<ul>
#{
var nodes1 = db.JobGroups.Where(jg => jg.CadreId == #node.Id).ToList();
foreach (var node1 in nodes1)
{
Cadre root1 = new Cadre();
root1.Id = node1.Id;
<li id="Gnode_#node1.Id">
#node1.Name
<ul>
#{
var nodes2 = db.JobGroupJobLevels.Where(jl => jl.JobGroup == #node1.Id).ToList();
foreach (var node2 in nodes2)
{
Cadre root2 = new Cadre();
root2.Id = node2.Id;
<li id="Lnode_#node2.Id">
#node2.JobLevel1.Name
<ul></ul>
</li>
}
}
</ul>
</li>
}
}
</ul>
</li>
}
}
</ul>
</div>
Update after first answer
doesn't work
Razor understand it as c# and tried to enclose it with double quotes doesn't work because the literal contains already doubles quotes then tried to replace " with \" this doesnt work because it doesn't give a meaning to the js Tree i am building
i found the solution elsewhere
i think there is an issue on adding server side code inside html tags like this
< li /* adding server code here leads in many inconvenient issues */ >
i found the solution by adding #:< / li > at the end of the li instead of just < / li >
Oh I Forgot to put the quotes around the attribute.
I think using a conditional operator might solve the issue.
#using TheodorHR_App.Models
<div id="tree_CadreGroupLevel" class="tree-demo">
<ul>
#{
TheodorHrEntities db = new TheodorHrEntities();
var nodes = db.Cadres.ToList();
foreach (var node in nodes)
{
Cadre root = new Cadre();
root.Id = node.Id;
<li id="Cnode_#node.Id" #(Model.RuleElementCadres.Select(e => e).Where(e => e.Cadre == node.Id).Count() > 0 ? "data-jstree='{ 'selected' : true }'" : "") >
#node.Name
<ul>
#{
var nodes1 = db.JobGroups.Where(jg => jg.CadreId == #node.Id).ToList();
foreach (var node1 in nodes1)
{
Cadre root1 = new Cadre();
root1.Id = node1.Id;
<li id="Gnode_#node1.Id">
#node1.Name
<ul>
#{
var nodes2 = db.JobGroupJobLevels.Where(jl => jl.JobGroup == #node1.Id).ToList();
foreach (var node2 in nodes2)
{
Cadre root2 = new Cadre();
root2.Id = node2.Id;
<li id="Lnode_#node2.Id">
#node2.JobLevel1.Name
<ul></ul>
</li>
}
}
</ul>
</li>
}
}
</ul>
</li>
}
}
</ul>
I have created a page to display list of questions to user & read user input for each question.
Issue: When user submits the Form, Model Parameter is null.
Post Action of the View is defined as below -
[HttpPost]
public ActionResult Index(IEnumerable<Question> model)
{
return View(model);
}
Code to display options to user is as below -
#foreach (var quest in Model)
{
<li>
#Html.LabelFor(x => quest.Title, quest.Title)
<ol class="Opt">
#foreach (var opt in quest.Options)
{
<li>#Html.RadioButtonFor(o => opt, opt.Title)
#Html.LabelFor(o => opt.Title, opt.Title)
</li>
}
</ol>
</li>
}
Here model is #model List<LakshyaMvc.Models.Question> and of course I have wrapped the code inside #using (Html.BeginForm())
Change your View Model.
#using (Html.BeginForm("Index", "Queries", FormMethod.Post))
{
for (int i = 0; i < Model.Count; i++)
{
<li>
#Html.LabelFor(x => Model[i].Question, Model[i].Question)
<ol class="Opt">
#for (int j = 0; j < Model[i].Options.Count; j++)
{
<li>#Html.RadioButtonFor(o => Model[i].Options[j].Option, false)
#Html.LabelFor(o => Model[i].Options[j].Option,
Model[i].Options[j].Option)
</li>
}
</ol>
</li>
<input type="submit" name="Submit" value="Submit" />
}
}
I need to create Menu for the master page. I've faced with following problem
<ul class="main_menu">
#foreach (var node in Model.Nodes)
{
int i = 1;
<li class="**HOW TO ADD HERE A CLASS like level+i.ToString()?????**">#Html.DisplayFor(m => node) |
#if (node.Children.Any()) {
<ul class="menuchild" style="display: none;">
<li>
#Html.DisplayFor(m => node.Children)
</li>
</ul>
}
</li>
}
</ul>
I need to create levels for the menu for Javascript , say level1 , level2 , level3 , how to combine strings inside Razor.
Thanks.
Enclose with #()
<li class="#("level" + i.ToString() )">
or
<li class="#string.Format("level{0}", i)">
How to Display the following
public ActionResult Index()
{
IEnumerable<int> items = Enumerable.Range(1000, 5);
ViewData["Collection"] = items;
return View();
}
in "View"
<ul>
<% foreach(int i in (IEnumerable)ViewData["Collection"]){ %>
<li>
<% =i.ToString(); }%>
</li>
</ul>
the foreach throws System.Web.HttpCompileException.
You had the closing brace of the foreach's loop in the wrong place. This is what you need:
<ul>
<% foreach (int i in (IEnumerable)ViewData["Collection"]) { %>
<li>
<%= i.ToString() %>
</li>
<% } %>
</ul>
And you also had some other extra punctuation in there as well (such as an extra semicolon).
I render a list of items like:
<ul>
<li>Something 1</li>
<li>Something 2</li>
<li>Something 3</li>
<li>Something 4</li>
<li>Something 5</li>
</ul>
Depending on the route I want to add a class to one of the <li> tags so that I can highlight.
Maybe something like:
<ul>
<% if (this.Context.Request.RawUrl.Contains(something1Var)) { %>
<li class="highlight">
<% } else { <%>
<li>
<% } %>
Something 1</li>
<% if (this.Context.Request.RawUrl.Contains(something2Var)) { %>
<li class="highlight">
<% } else { <%>
<li>
<% } %>
Something 2</li>
<% if (this.Context.Request.RawUrl.Contains(something3Var)) { %>
<li class="highlight">
<% } else { <%>
<li>
<% } %>
Something 3</li>
<% if (this.Context.Request.RawUrl.Contains(something3Var)) { %>
<li class="highlight">
<% } else { <%>
<li>
<% } %>
Something 4</li>
<% if (this.Context.Request.RawUrl.Contains(something5Var)) { %>
<li class="highlight">
<% } else { <%>
<li>
<% } %>
Something 5</li>
</ul>
It does work but it seems a bit verbose. Can anyone suggest a better method of doing this sort of thing?
I'd argue that this kind of logic is better isolated in the controller. Consider making a lightweight class to represent your menu items, like this:
public class MenuLinkItem {
public string Text { get; set; }
public bool Highlight { get; set; }
}
Then in your controller method, build a list of these, set the CSS class on the highlighted element, and pass the result to the view via the ViewData:
public class MyController : Controller {
private MenuLinkItem MakeMenuLinkItem(string text, string urlFragment) {
return (new MenuLinkItem() {
Text = text,
Highlight = (this.Context.Request.RawUrl.Contains(urlFragment))
}
}
private IList<MenuLinkItem> GetMenuLinkItems() {
var items = new List<MenuLinkItem>();
items.Add(MakeMenuLinkItem("Something 1", something1var));
items.Add(MakeMenuLinkItem("Something 2", something2var));
items.Add(MakeMenuLinkItem("Something 3", something3var));
items.Add(MakeMenuLinkItem("Something 4", something4var));
items.Add(MakeMenuLinkItem("Something 5", something5var));
return(items);
}
public ActionResult Index() {
ViewData["menuLinkItems"] = GetMenuLinkItems();
/* other controller logic here */
return(View());
}
}
Then, in your actual view code, you render your menu like this:
<ul>
<% foreach(var item in (IList<LinkMenuItem>)ViewData["menuLinkItems"])) { %>
<li <%= item.Highlight ? "class=\"highlight\"" : ""%>><%=item.Text%></li>
<% } %>
</ul>
The controller's making the decisions about which links are highlighted, and the view is converting those decisions into an HTML/CSS representation that makes sense to your users.