I have a template:
<asp:Repeater ID="litFolder" runat="server" OnItemDataBound="litFolder_ItemDataBound">
<HeaderTemplate>
<ul class="test" id="currentLink">
</HeaderTemplate>
<ItemTemplate>
<div class="leftNav">
<li>
<asp:HyperLink ID="innerHyperLink" runat="server"></asp:HyperLink>
</li>
</div>
</ItemTemplate>
<FooterTemplate>
</ul>
</FooterTemplate>
</asp:Repeater>
and I'm trying to set the to display block when a link is selected. I can set the link to display block, but how do I set the ul to display block ( only using C# )
protected void litFolder_ItemDataBound(object sender, RepeaterItemEventArgs e)
{
// if the child from the first repeater has children, it will grab them here
Item innerItem = (Item)e.Item.DataItem;
if (innerItem != null)
{
if (e.Item.ItemType == ListItemType.Item || e.Item.ItemType == ListItemType.AlternatingItem)
{
// this creates a link to the page in sitecore once clicked
HyperLink topNavigation = (HyperLink)e.Item.FindControl("innerHyperLink");
topNavigation.NavigateUrl = LinkManager.GetItemUrl(innerItem);
topNavigation.Text = innerItem["Title"];
if (topNavigation != null) {
//this is where I think I need to define the ul to display block
}
}
}
}
I need to make sure that the current link sets the ul that it is in and not all the ul's with the class test.
In order to prevent the Ul from being broken, place the <div class="leftNav"> inside the <li> as shown below:
<asp:Repeater ID="litFolder" runat="server" OnItemDataBound="litFolder_ItemDataBound">
<HeaderTemplate>
<ul class="test" id="currentLink">
</HeaderTemplate>
<ItemTemplate>
<li>
<div class="leftNav">
<asp:HyperLink ID="innerHyperLink" runat="server"></asp:HyperLink>
</div>
</li>
</ItemTemplate>
<FooterTemplate>
</ul>
</FooterTemplate>
To set the display block style, you can find the control based on the ID, then set the style to it.
Thanks
Related
I have a repeater inner another repeater and this second one i have a list of checkbox and i need to get the value of the checked.
This is my front code:
<asp:Repeater runat="server" ID="rptPerfis" OnItemDataBound="ItemBound">
<ItemTemplate>
<div class="mws-form-row">
<ul class="mws-form-list inline" style="float: none; display: inline;">
<li style="padding-top: 10px;">
<%# rptNome(Container) %></li>
</ul>
<asp:Repeater runat="server" ID="rptUsers">
<ItemTemplate>
<div class="mws-form-item radioPermissoes clearfix" style="float: none;">
<ul class="mws-form-list inline">
<li>
<asp:CheckBox runat="server" Text="<%# rptAdministradorNome(Container) %>" ID="checkUser" CssClass="<%# rptAdministradorPostClass(Container) %>" /></li>
</ul>
</div>
</ItemTemplate>
</asp:Repeater>
</div>
<br />
<hr />
</ItemTemplate>
</asp:Repeater>
<asp:LinkButton runat="server" ID="fLnkSalvar" class="mws-ic-16 ic-disk" OnClick="fLnkSalvar_Click">Salvar</asp:LinkButton>
and this is how i fill this repeater:
protected void Page_Load(object sender, EventArgs e)
{
listaAdm = Servicos.AdministradorMySql.ListarEmpresa(denuncia.Empresa).OrderByDescending(x => x.Nome).ToList();
todosPerfis = Servicos.Perfil.ListarTodos().ToList();
rptPerfis.DataSource = todosPerfis.Where(x => x.Ativo).OrderBy(x => x.Nome);
rptPerfis.DataBind();
}
protected void ItemBound(object sender, RepeaterItemEventArgs args)
{
if (args.Item.ItemType == ListItemType.Item || args.Item.ItemType == ListItemType.AlternatingItem)
{
int idPerfil = ((Perfil)args.Item.DataItem).ID;
Repeater childRepeater = (Repeater)args.Item.FindControl("rptUsers");
childRepeater.DataSource = listaAdm.Where(x => x.Perfil > 1 && x.Perfil == idPerfil).ToList();
childRepeater.DataBind();
}
}
protected void fLnkSalvar_Click(object sender, EventArgs e)
{
Administrador usuario = new Administrador();
usuario.Permissoes = new List<string>();
// i need to get this values here to fill this `List<string>` and then save
foreach (var x in usuario.Permissoes)
{
Servicos.Denuncia.InserirUsuarios(denuncia.ID, x);
}
}
I've no idea how can i get this values or if there another easier way without add in the list i think its better
You have to use FindControl on multiple levels. First the correct Item in the parent Repeater, then find the CheckBox in the correct Item of the child Repeater.
var cb = ((Repeater)rptPerfis.Items[i].FindControl("rptUsers")).Items[j].FindControl("checkUser") as CheckBox;
PS you need to wrap the code in Page_Load in an IsPostBack check or you will never retrieve the correct checkbox state in a PostBack.
I have this functions that gets categories in three levels.
One that gets ParentCategories
One that gets categories by ParentCategoryID
One that gets Subcategories by categoriesID.
I want to build a megamenu looking like this site:
http://www.potterybarn.com/
HTML Markup
<div>
<asp:Repeater ID="HorizMenuRepeater" runat="server">
<HeaderTemplate>
<ul id="mega-menu"></HeaderTemplate>
<ItemTemplate>
<li><a id="mBox" href="javascript:;">'<%#Eval("ParentCatName")%>'</a></li></ItemTemplate>
<FooterTemplate></ul></FooterTemplate></asp:Repeater>
</div>
<script>
window.addEvent('domready', function () {
new mBox.Tooltip({
content: 'MegamenuUC',
setStyles: { content: { padding: 15, lineHeight: 20 } },
position: {
x: 'right',
y: 'bottom'
},
attach: 'mBox',
closeOnMouseleave: true
});
});
</script>
<div id="MegamenuUC" style="display:none">
<uc1:Megamenu ID="Megamenu1" runat="server" />
</div>
result
Code of the usercontrol
<ul>
<h3>Category</h3>
<ul>
<li>Sub category</li>
</ul>
</ul>
I want to make this dynamically, now it's just the parentcategory that is dynamic.
I need somehow pass the id to know witch parentcategory you hovered over tho pas the right id to my function that gets the categories so I can populate my usercontrol with it
Thanks
I solved it and i used a repeater to create a clean list and a jquery plugin to create megamenu
Link to jquery plugin http://www.designchemical.com/lab/jquery-mega-drop-down-menu-plugin/options/
Code for databind repeater with linq
<div>
<asp:Repeater ID="ParentRepeater" runat="server" OnItemDataBound="ParentRepeater_OnItemBound">
<HeaderTemplate>
<ul>
</HeaderTemplate>
<ItemTemplate>
<li><a><%# DataBinder.Eval(Container.DataItem, "ParentCatName") %></a>
<asp:Repeater ID="ParentCatRepeater" runat="server" OnItemDataBound="ChildRepeater_OnItemBound">
<HeaderTemplate>
<ul>
</HeaderTemplate>
<ItemTemplate>
<li><a><%# DataBinder.Eval(Container.DataItem, "CategoryName") %></a>
<asp:Repeater ID="ChildRepeater" runat="server">
<HeaderTemplate>
<ul>
</HeaderTemplate>
<ItemTemplate>
<li><a><%# DataBinder.Eval(Container.DataItem, "ProductName") %></a></li>
</ItemTemplate>
<FooterTemplate></ul></FooterTemplate>
</asp:Repeater>
</li>
</ItemTemplate>
<FooterTemplate></ul></FooterTemplate>
</asp:Repeater>
</li>
</ItemTemplate>
<FooterTemplate></ul></FooterTemplate>
</asp:Repeater>
</div>
C#
protected void Page_Load(object sender, EventArgs e)
{
LinqtoDBDataContext db = new LinqtoDBDataContext();
ParentRepeater.DataSource = db.GetParentCategories();
ParentRepeater.DataBind();
}
protected void ParentRepeater_OnItemBound(object sender, RepeaterItemEventArgs e)
{
if (e.Item.ItemType == ListItemType.Item || e.Item.ItemType == ListItemType.AlternatingItem)
{
dynamic cat = e.Item.DataItem as dynamic;
int parentcatid = Convert.ToInt32(cat.ParentCatID);
LinqtoDBDataContext db = new LinqtoDBDataContext();
//var cats = from c in db.Categories
// where c.ParentCatID == parentcatid
// select c;
Repeater ParentCatRepeater = e.Item.FindControl("ParentCatRepeater") as Repeater;
ParentCatRepeater.DataSource = db.GetCategories(parentcatid);
ParentCatRepeater.DataBind();
}
}
protected void ChildRepeater_OnItemBound(object sender, RepeaterItemEventArgs e)
{
if (e.Item.ItemType == ListItemType.Item || e.Item.ItemType == ListItemType.AlternatingItem)
{
dynamic prod = e.Item.DataItem as dynamic;
int catid = Convert.ToInt32(prod.CategoryID);
LinqtoDBDataContext db = new LinqtoDBDataContext();
Repeater ChildRepeater = e.Item.FindControl("ChildRepeater") as Repeater;
ChildRepeater.DataSource = db.GetProductsInCategory(catid);
ChildRepeater.DataBind();
}
}
}
Kinda of confusing title.
This is my old navigation
<li><i class="home"></i> Overview</li>
The i class sets an icon next to the navigation tab.
On the Site.Master.CS I checked what the current page was and would set it to active with the code below.
currentGeneral.Attributes["class"] = "active";
So I changed the navigation to a listview populated by a database.
<asp:ListView ID="ListViewMenu" runat="server" ItemPlaceholderID="menuContainer">
<LayoutTemplate>
<ul class="menu" id="responsive" runat="server">
<asp:PlaceHolder ID="menuContainer" runat="server" />
</ul>
</LayoutTemplate>
<ItemTemplate>
<li><a href='<%#Eval ("href") %>' class='<%#Eval ("id") %>'> <i class='<%#Eval ("class") %>'></i><%#Eval ("text") %></a></li>
</ItemTemplate>
</asp:ListView>
But now that I am using listview, the currentGeneral id does not exist and I cant set it to active.
I was trying to think what the best way to get this to work is. Anyone have a suggestion?
Thank you.
If you want to access individual item inside of ListView while binding, you might want a different approach using ItemDataBound event.
Please make sure to cast DataItem to appropiate object. For example, DataRowView
<asp:ListView ID="ListViewMenu" runat="server"
OnItemDataBound="ListViewMenu_ItemDataBound"
ItemPlaceholderID="menuContainer">
<LayoutTemplate>
<ul class="menu" id="responsive" runat="server">
<asp:PlaceHolder ID="menuContainer" runat="server" />
</ul>
</LayoutTemplate>
<ItemTemplate>
<li>
<asp:HyperLink runat="server" ID="HyperLink1" >
<i class='<%#Eval ("class") %>'></i><%#Eval ("text") %>
</asp:HyperLink>
</li>
</ItemTemplate>
</asp:ListView>
protected void Page_Load(object sender, EventArgs e)
{
if (!IsPostBack)
{
PopulateMenu();
}
}
protected void ListViewMenu_ItemDataBound(
object sender, ListViewItemEventArgs e)
{
if (e.Item.ItemType == ListViewItemType.DataItem)
{
var rowView = e.Item.DataItem as DataRowView;
var hyperLink = e.Item.FindControl("HyperLink1") as HyperLink;
hyperLink.NavigateUrl = rowView["href"].ToString();
hyperLink.CssClass = rowView["menu"].ToString();
if (Request.Path.ToLower().Contains(rowView["href"].ToString()))
hyperLink.CssClass += " active";
}
}
void PopulateMenu()
{
DataAccess da = new DataAccess();
da.AddParameter("ID", ID, DataAccess.SQLDataType.SQLInteger, 4);
SiteMenu = da.runSPDataSet("Portal_MenuCreate");
ListViewMenu.DataSource = SiteMenu;
ListViewMenu.DataBind();
}
I have a search results page where the list views visible property is always false on the first page load even though I set the value to true as seen below. It seems line is being ignored? Is there a reason why this property cannot be set on the first load?
EDIT: Page load Event
protected void Page_Load(object sender, EventArgs e)
{
if (!IsPostBack)
{
if (Request.QueryString["query"] != null)
{
_searchTerm = Request.QueryString["query"].ToString();
GetSearchResults();
txtSearchBox.Text = _searchTerm;
}
}
}
ListView Markup
<asp:PlaceHolder runat="server" ID="SearchResults" Visible="false">
...
<asp:ListView id="lvSearch" runat="server">
<LayoutTemplate>
<ul id="SearchResultsList">
<asp:PlaceHolder runat="server" ID="itemPlaceholder"></asp:PlaceHolder>
</ul>
</LayoutTemplate>
<ItemTemplate>
<li class="searchResult">
<h2><%#DataBinder.Eval(Container.DataItem, "Title")%></h2>
<p><%#DataBinder.Eval(Container.DataItem, "HighlightedPreview")%></p>
<%#DataBinder.Eval(Container.DataItem, "URL")%>
</li>
</ItemTemplate>
</asp:ListView>
<div runat="server" id="NoResults" visible="false">
<p>The current search has returned no results. Please enter another search term in the box above.</p>
</div>
</asp:PlaceHolder>
Check that it is not in the DIV-NoResults or some other container that is going invisible.
I have a nested repeater control that displays a list of data, in my case it is an FAQ list. here is the design portion:
<asp:Repeater ID="lists" runat="server">
<ItemTemplate>
<h2 class="sf_listTitle"><asp:Literal ID="listTitle" runat="server"></asp:Literal></h2>
<p class="sf_controlListItems">
<a id="expandAll" runat="server">
<asp:Literal ID="Literal1" runat="server" Text="<%$Resources:ExpandAll %>"></asp:Literal>
</a>
<a id="collapseAll" runat="server" style="display:none;">
<asp:Literal ID="Literal2" runat="server" Text="<%$Resources:CollapseAll %>"></asp:Literal>
</a>
</p>
<ul class="sf_expandableList" id="expandableList" runat="server">
<asp:Repeater ID="listItems" runat="server">
<HeaderTemplate>
</HeaderTemplate>
<ItemTemplate>
<li>
<h1 id="headlineContainer" runat="server" class="sf_listItemTitle">
<a id="headline" runat="server" title="<%$Resources:ClickToExpand %>"></a>
</h1>
<div id="contentContainer" runat="server" class="sf_listItemBody" style="display:none;">
<asp:Literal ID="content" runat="server"></asp:Literal>
</div>
</li>
</ItemTemplate>
<FooterTemplate>
</FooterTemplate>
</asp:Repeater>
</ul>
</ItemTemplate>
</asp:Repeater>
The repeater that I am interested in is the second repeater, listItems. In my code-behind, I cannot directly call listItems and see the controls inside of it. I tried to grab the control inside of list.DataBinding (maybe I need to use a different event?) method:
void lists_ItemDataBound(object sender, RepeaterItemEventArgs e)
{
var oRepeater = (Repeater) lists.FindControl("listItems");
}
but this comes up as null. Can anyone give me some pointers/tips of what I need to do to gain access to the listItems repeater and it's children controls?
Thanks!
lists
belongs to each RepeaterItem, not directly to the Repeater itself.
Try :-
void lists_ItemDataBound(object sender, RepeaterItemEventArgs e)
{
if ( e.Item.ItemType == ListItemType.AlternatingItem
|| e.Item.ItemType == ListItemType.Item )
{
Repeater oRepeater = (Repeater)e.Item.FindControl("listItems");
// And to get the stuff inside.
foreach ( RepeaterItem myItem in oRepeater.Items )
{
if ( myItem.Item.ItemType == ListItemType.AlternatingItem
|| myItem.Item.ItemType == ListItemType.Item )
{
Literal myContent = (Literal)myItem.FindControl("content");
// Do Something Good!
myContent.Text = "Huzzah!";
}
}
}
}
And you should be good :)
Edited to incorporate DavidP's helpful refinement.
You need to change that line to
var oRepeater = (Repeater) e.Item.FindControl("listItems");
You're close! Inside your event handler check the RepeaterItemEventArgs for what kind of row you're dealing with. Your child repeater will only be available on (Alt)Item rows, not headers or footers. My guess is that it's blowing up on the header.