Display Nested ListViews (Menus to Submenus) with AccessDataSource - asp.net

Good Days,
By using ASP.NET and AccessDataSource, I need to display a listview inside a parent listview to be able to have menus and their submenus. Current state of my code is:
<asp:AccessDataSource ID="adsMenus" runat="server" DataFile="~/App_Data/menus.accdb" SelectCommand="SELECT MenuID, Menu FROM Menus" />
<asp:ListView ID="lvwMenus" runat="server" DataSourceID="adsMenus" DataKeyNames="MenuID">
<ItemTemplate>
<h2><%#Eval("Menu")%></h2>
<asp:AccessDataSource ID="adsSubmenus" runat="server" DataFile="~/App_Data/menus.accdb" SelectCommand="SELECT Submenu FROM Submenus WHERE MenuID = <%#Eval('MenuID')%>" />
<asp:ListView ID="lvwSubmenus" runat="server" DataSourceID="adsSubmenus">
<ItemTemplate>
<h3><%#Eval("Submenu")%></h3>
</ItemTemplate>
</asp:ListView>
</ItemTemplate>
</asp:ListView>
When I debug and run the page, it gives a syntax error. I am in the phase of learning ASP.NET with C# and I believe this should be an easy fix but somehow I couldn't find a simple solution after reading several blogs and posts.
Thank you for your help and time!

Attribute that has a value formed from literals and evaluated fields should be, as a rule, constructued wholly in the <%# %>:
SelectCommand='<%# string.Format("SELECT Submenu FROM Submenus WHERE MenuID = {0}", Eval("MenuID")) %>'

Related

Nested CheckBoxList using DataSet and Repeaters

I'm trying to wire up some CBL's using a repeater and dataset. The dataset contains 2 tables with the same schema and a (one, single) relation (in SQL land think of it as a self join).
When the control is rendered if I set my DataSource = the relationship, I am able to get the children elements to show; so I know the model is good, although misplaced (on purpose to test the model - see code below).
The problem is:
I am having difficulty getting the parent elements to show up at all
Not all parents have children, and the ones that don't still need to show up
Am I approaching this in the right frame of mind? i.e. Am I missing something fundamental? Implementation outside of CBL(plain text) works fine per this article
<asp:Repeater ID="ParentRepeater" runat="server">
<ItemTemplate>
<asp:CheckBoxList ID="ParentCBL" runat="server"
DataSource='<%# DataBinder.Eval(Container.DataItem,"Joined") %>'
DataTextField="TextProperty"
DataValueField="ValueProperty">
</asp:CheckBoxList>
<asp:Repeater ID="ChildRepeater" runat="server">
<ItemTemplate>
<asp:CheckBoxList ID="ChildCBL" runat="server"
DataSource='<%# DataBinder.Eval(Container.DataItem, "Joined") %>'
DataTextField="TextProperty"
DataValueField="ValueProperty">
</asp:CheckBoxList>
</ItemTemplate>
</asp:Repeater>
</ItemTemplate>
</asp:Repeater>
Page Load is nothing spectacular
DataSet ds = Foo.foo();
ParentRepeater.DataSource = ds.Tables["Parent"];
ParentRepeater.DataBind();
In your code you don't bind ChildRepeater
If you want just change plain text to Checkbox in according to https://support.microsoft.com/en-us/kb/306154
then you don't need to use CheckBoxList. But you should only use single checkbox inside repeater.

Passing Value Through Link Button in ASP.NET

Conditions :
I have two tables,
category(id_kat,name_kat)
book(id_book,id_kat,name_book)
id_kat has a child and parent relations.
I'm a little bit confused using ASP.NET, especially when passing value between pages.
Now, i'm showing the category's datas with
<asp:listview id="listview1" runat="server" datakeynames"id_kat" datasourceID="sdskat">
//FYI sdskat is datasource for category table
<itemtemplate>
<li>
<asp:linkbutton id="linking" runat="server" ><%# Eval("name_kat") %></asp:linkbutton>
</li>
</itemtemplate>
</asp:listview>
The problem is, i wanted to pass "id_kat" value when i click the hyperlink. (but redirected to self page).
I want it as a query string (or another way if able).
Thanks a lot.
If you're linking to the same page with different query string parameters, you only need to include ? and after.
<%# Eval("name_kat") %>
You could use <asp:hyperlink id="linking" runat="server" ><%# Eval("name_kat") %></asp:hyperlink> instead. You can then add your url in the navigateURL attribute and append your id_kat on there.
Something like this should work:
<asp:hyperlink id="linking" runat="server" navigateURL="~/page.aspx?id_kat=<%# Eval('id_kat') %>" ><%# Eval("name_kat") %></asp:hyperlink>
the <asp:hyperlink> tag is essentially the tag but using a server side control.
If you have to use a linkbutton then in your code behind you can append the id_kat to the querystring and then response.redirect(url) to the new page.
Why not use a regular anchor?
<a href='foo.aspx?id=<%# Eval("id_kat") %>'><%# Eval("name_kat") %></a>

How to update an ASP.NET label with SqlDataSource return value

On an ASP.NET page, I have a SqlDataSource configured with the following SELECT command:
SELECT AVG(Rating) FROM [Ratings] WHERE ([AlbumID] = #AlbumID)
How would I place that average value into a label?
You need to use FormView control to put the Label in.
Something like this:
<asp:formview id="formview1" runat="server" datasourceid="your-datasource-id">
<itemtemplate>
<asp:label id="label1" runat="server" text='<%# Eval("column-name") %>' />
</itemtemplate>
</asp:formview>
Replace your-datasource-id and column-name in the above code.
PS: you might need to alter the query to have a column-name for that one value:
SELECT AVG(Rating) AS "average" FROM [Ratings] WHERE ([AlbumID] = #AlbumID)

asp.net repeater with usercontrol - setting commandargument

I have the following repeater code:
<asp:Repeater ID="repMain" runat="server" OnItemCommand="repMain_ItemCommand" EnableViewState="false">
<ItemTemplate>
<dmg:testcontrol runat="server" MyData=<%#Container.DataItem %>>
</dmg:testcontrol>
</ItemTemplate>
</asp:Repeater>
The testcontrol usercontrol looks like:
<%# Control Language="C#" AutoEventWireup="true" CodeBehind="TestControl.ascx.cs" Inherits="TestRepeater.TestControl" %>
<asp:Literal runat="server" ID="litMain" Text="<%#MyData.MyValue %>"></asp:Literal>
<asp:DropDownList runat="server" ID="dropdownMain"></asp:DropDownList>
<asp:Button runat="server" ID="btnMain" Text="Click Me" CommandName="Update" CommandArgument="<%#dropdownMain.SelectedValue%>"/>
Is it possible for me to send through the dropdownMain.SelectedValue as the CommandArgument?
Just now it is an empty string.
Thanks
Duncan
PS This is related to ASP.NET Repeater not binding after ItemCommand but I thought the two sufficiently different to keep apart.
A bit old question but I just my self found the answer to this one.
CommandArgument="<%#dropdownMain.SelectedValue%>"
Needs to look like this instead with single quotes! All inline codes within a asp.net controls have to be done this way instead.
CommandArgument='<%#dropdownMain.SelectedValue%>'
Why not get the selected value, and use it inside the Command function ?
(why to try to send it as argument, from the moment you can get it inside the command called function and its the same)

How do I data bind a drop down list in a gridview from a database table using VB?

So in this gridview, there is a column for status and I want to have a drop down list with Pass, Pending, Fail appear when the edit button is clicked. These values are already in a table, so I need to somehow bind from this table to each ddl for every row.
Here is the column from the gridview. As you can see, I would like to just have a label showing when not in edit mode, and a ddl when the edit button is pressed
<asp:TemplateField HeaderText="During Production Status" SortExpression="DuringProductionStatus">
<EditItemTemplate>
<asp:DropDownList ID="ddlStatus" runat="server" datavaluefield="Name"
datatextfield="Name" DataSource="*What goes here?*"> />
</EditItemTemplate>
<ItemTemplate>
<asp:Label ID="lblStatus" runat="server"
Text='I don't understand how to get this from the ddl' />
</ItemTemplate>
</asp:TemplateField>
For clarity's sake, my table is named Status, and the database is named DirectImport
There's a few steps to go through here - none of them are particularly difficult, but they can be a bit fiddly (IMHO). The good news is once you've got this working once, it gets easier to do it again!
I'm assuming you've got a <asp:*DataSource> control on your page - my preference is for an ObjectDataSource but I don't think it matters, I think a SqlDataSource works equally well. I've never tried doing this with GridView.DataSource = MyDataSet in code-behind, so I don't know whether that would work or not, but my assumption is that it wouldn't as you wouldn't get the proper two-way binding that you want. This data source feeds your grid with your main data. The key point here is that your database query must return both the Status text field and the Status id.
So your gridview will now look something like:
<asp:objectdatasource runat="server" id="MainDataSource" ... />
<asp:gridview runat="server" id="MyGridView" DataSourceID="MainDataSource">
<Columns>
<asp:TemplateField HeaderText="During Production Status" SortExpression="DuringProductionStatus">
<ItemTemplate>
<asp:Label ID="lblStatus" runat="server"
Text="<%# Bind('Status') %>" />
</ItemTemplate>
</asp:TemplateField>
</Columns>
</asp:gridview>
The Text="<%# Bind('Status') %>" is the bit you're missing to get the status text into the grid.
Now add a second data source into your markup that reads in the set of values from the Status table.
<asp:objectdatasource runat="server" id="StatusObjectDataSource" ... />
And add the EditItemTemplate into the GridView, which is bound to the Status DataSource.
<EditItemTemplate>
<asp:DropDownList ID="ddlStatus" runat="server" datavaluefield="StatusID"
datatextfield="Status" DataSourceID="StatusObjectDataSource"
SelectedValue="<%# Bind('StatusId') %>" />
</EditItemTemplate>
The SelectedValue="<%# Bind('StatusId') %>" is what connects up the two datasets so that when you flip a row into Edit mode, the dropdownlist has the correct item already selected, and when you then save it you've got the Status ID to put into your database.
And you're done.
I have used the RowDataBound event. Here is a small code snippet. HTH
you would have an ItemTemplate in your aspx/ascx
<asp:TemplateField HeaderText="Column Headings">
<ItemTemplate>
<asp:DropDownList ID="ddlName" runat="server" Width="150"></asp:DropDownList>
</ItemTemplate>
</asp:TemplateField>
and in your code behind, you will have
protected void grdDataMap_RowDataBound(object sender, GridViewRowEventArgs e)
{
if (e.Row.RowType == DataControlRowType.DataRow)
{
DropDownList ddl = (DropDownList)e.Row.FindControl("ddlName");
ddl.DataSource = someList;//the source of your dropdown
ddl.DataBind();
}
}
so when you bind your grid with grdDataMap.Databind (assuming your grid id is grdDataMap), row databound event will be called for each row (including header/footer, and thats the reason you check RowType)
so you can probably decide what controls/columns to hide/show/bind inside this row databound event
In the winforms world I pull my objects from the DB into a List(Of Whatever) and use the list as the datasource.
This also lets me add extra "convenience" fields in the object so that I can populate it with stuff from other tables.
I don't know asp.net at all so if you can do something similar, it might help.
A really quick solution is to create a custom web control for the status dropdown. The control will always contain the same data. When it renders you populate the datasource. When it gets added to the gridview, the data will be in the drop down. Hope that helps!

Resources