Make gridview datasource stay in interface not cast down to object - c#

I have a C# web app where I have a gridview that takes a List<> that takes an interface. There are three object types that implement the interface that are within the list.
I set the gridviews datasource to the list and call databind. When I run the app I get the following error:
{"Property accessor 'Name' on object 'Bailey.Objects.Company' threw the following exception:'Object does not match target type.'"}
I changed the object order around in the list and found that the first object type works just fine but when it finds the first instance of another object it throws this error.
List<IBaileyObject> listToDisplay = listofItems;
GridViewItemList.DataSource = listToDisplay;
GridViewItemList.DataBind();
What I wanted was for the datasource and binding to stay on the interface rather then cast down to the object as it would seem to be happening.
Is this because the List<> is returning the object as it self rather than the Interface or is it something in the gridview that is casting it down?
Or am I going down the wrong track?
I hope someone has a way to fix this please.
Thanks
Jon Hawkins
EDIT
<asp:TemplateField HeaderText="Selected">
<ItemTemplate>
<asp:CheckBox runat="server" ID="chkbox" Width="10%" Enabled="true" AutoPostBack="false" />
</ItemTemplate>
</asp:TemplateField>
<asp:BoundField DataField="ID" HeaderText="ID" Visible="False" />
<asp:BoundField DataField="Name" HeaderText="Name" />
<asp:BoundField DataField="TypeName" HeaderText="Type" />
</Columns>
<FooterStyle BackColor="#1C5E55" Font-Bold="True" ForeColor="White" />
<RowStyle BackColor="#E3EAEB" />
<PagerStyle BackColor="#666666" ForeColor="White" HorizontalAlign="Center" />
<SelectedRowStyle BackColor="#C5BBAF" Font-Bold="True" ForeColor="#333333" />
<HeaderStyle BackColor="#1C5E55" Font-Bold="True" ForeColor="White" />
<EditRowStyle BackColor="#7C6F57" />
<AlternatingRowStyle BackColor="#F8F8F8" />
The interface exposes Name, ID and TypeName.
" HeaderText="ID" Visible="False" />
gives can not apply indexer.

I really like this solution : http://iridescence.no/post/FixingBoundFieldSupportforCompositeObjects.aspx
It uses a custom BoundField class that uses the Eval to return the values. A little nicer than using the Evals in the ASPX page...

Can you post some of your GridView code (specifically where you reference your IBaileyObject properties)?
Not knowing what syntax you're using makes things hard, but have you tried doing something like this:
<%# (((IBaileyObject)Container.DataItem)["PropertyX"]) %>
Hope this helps
Edit after code posted
I think it's because you're using "BoundField"s - they're not clever enough to work out where the member you're referring to comes from. My advice is to convert your BoundFields to databinding syntax:
Either: <%# Eval("Id") %>
or, <%# (((IBaileyObject)Container.DataItem)["Id"]) %>
Failing that, follow the advice in this blog post and create a custom bound field control.

GridViewItemList.DataSource = listToDisplay.Select(x => new
{
Id = x.Id,
Name = x.Name
})
.ToList();
GridViewItemList.DataBind();

Related

ASP.Net Gridview Not Allowing Rows To be Selected After Certain Value In DataKey

I've been utilizing what I call, "drag, drop and configure" programming for years to create very simple ASP.net forms to collect data for my organization. Basically, I'll drag a datasource into my design view, configure it, and then I'll drag a gridview into the design view and then configure it, etc., etc.
Yesterday, I encountered a behavior I have never seen. My gridview is set to allow row selection. Everything seemed to be working normally until I happened to click on a row that didn't "select" (didn't highlight itself, etc.). And, then I started clicking on other rows and found more that couldn't be selected. Again -- it's not all the rows...just some. i.e. some can be selected and others can't.
After a lot of troubleshooting, the only thing I've been able to determine is that above a certain datakey value -- rows won't select. In this case, its datakeys with values around and > 40,000. Anything below that, and the rows select and the other parts of the form load just fine. The fact that it works for all records with datakeys below a certain value is really stumping me as to what rock to look under next -- hence, actually creating a stackoverflow account and posing the question.
Code for the gridview is below. It does live within an update panel if that matters. Also provided the code behind, though it's not really doing anything of consequence.
Note:
The datakey that seems to be controlling the behavior is a unique identifier for an application within a set of applications. It's not an incremental identity. --- if that helps.
The form is hooked into a database for the select statement and is pulling records from a view to populate the grid.
I'm tempted to show all of my code including the database side and stored procs -- thinking maybe I'm making rookie mistakes with data typing, etc. --- BUT --- I'm pausing there because the gridview selection IS WORKING -- just not above datakeys around and above 40,000
Lastly, when you attempt to select an item with a key > 40,000 the grid will no longer sort by columns or allow you to click a different page. Similarly, if you sort the grid FIRST by applicationID (the datakey) -- all the pages with datakeys > 40,000 are not clickable i.e. pagination for those pages do not work
EDIT --- DANG IT!!! I posted the wrong code behind. I replaced it with the right one. UPDATE: It looks like it's related to the panels. When I comment them out --- it works. When they are included -- the rows in question (keys > 40000) aren't selectable. All this code does is control visibility of panels. How could visibility properties make this kind of impact....weird
Pic of Issue:
<ContentTemplate>
<strong>
<asp:ScriptManager ID="ScriptManager2" runat="server">
</asp:ScriptManager>
Select AIT by using search box below or by sorting and paging through AIT table.<br />
<br />
Search: </strong> <asp:TextBox ID="TxtAITSearch" runat="server"></asp:TextBox>
<asp:Button ID="btn_Search" runat="server" OnClick="btn_Search_Click" Text="Search" />
<em>
<br />
*wildcard searches for AIT number, AIT Name or AIT Manager may be used</em><asp:HiddenField ID="hdnApl_ID" runat="server" />
<asp:HiddenField ID="hdn_StandardID" runat="server" />
<asp:HiddenField ID="Hdn_AlignmentID" runat="server" />
<asp:HiddenField ID="hdn_Attribute" runat="server" />
<br />
<asp:GridView ID="gvAITSelect" runat="server" AllowPaging="True" AllowSorting="True" AutoGenerateColumns="False" CellPadding="3" DataKeyNames="applicationID" DataSourceID="DSGetSearchView" GridLines="Vertical" OnSelectedIndexChanged="gvAITSelect_SelectedIndexChanged" BackColor="White" BorderColor="#999999" BorderStyle="None" BorderWidth="1px">
<AlternatingRowStyle BackColor="#DCDCDC" />
<Columns>
<asp:CommandField ShowSelectButton="True" />
<asp:BoundField DataField="applicationID" HeaderText="App ID" SortExpression="applicationID" />
<asp:BoundField DataField="fullName" HeaderText="Application" SortExpression="fullName" />
<asp:BoundField DataField="Alignment" HeaderText="Alignment" SortExpression="Alignment" />
<asp:BoundField DataField="AlignmentID" HeaderText="AlignmentID" SortExpression="AlignmentID" Visible="False" />
<asp:BoundField DataField="status" HeaderText="Status" SortExpression="status" />
<asp:BoundField DataField="relatedAssociates_2_displayName" HeaderText="App Mgr" SortExpression="relatedAssociates_2_displayName" />
<asp:BoundField DataField="relatedAssociates_3_displayName" HeaderText="Tech Exec" SortExpression="relatedAssociates_3_displayName" />
</Columns>
<FooterStyle BackColor="#CCCCCC" ForeColor="Black" />
<HeaderStyle BackColor="#000084" Font-Bold="True" ForeColor="White" />
<PagerStyle BackColor="#999999" ForeColor="Black" HorizontalAlign="Center" />
<RowStyle BackColor="#EEEEEE" ForeColor="Black" />
<SelectedRowStyle BackColor="#008A8C" Font-Bold="True" ForeColor="White" />
<SortedAscendingCellStyle BackColor="#F1F1F1" />
<SortedAscendingHeaderStyle BackColor="#0000A9" />
<SortedDescendingCellStyle BackColor="#CAC9C9" />
<SortedDescendingHeaderStyle BackColor="#000065" />
</asp:GridView>
protected void gvAITSelect_SelectedIndexChanged(object sender, EventArgs e)
{
lbl_Alignment.Text = gvAITSelect.SelectedRow.Cells[3].Text;
Hdn_AlignmentID.Value = gvAITSelect.SelectedRow.Cells[4].Text;
string strAITvalue = gvAITSelect.SelectedRow.Cells[1].Text;
hdnApl_ID.Value = strAITvalue.ToString();
//panel_RoleDetails.Visible = true;
//panel_AITAlignment.Visible = true;
//panel_NoteDetails.Visible = true;
}
Ok -- I figured it out. And, the answer is, I'm a big dummy. Further, the fact that the grid stopped working around in and around 40000 should have been a big flashlight to me pointing the way. Pic of the issues
If you look at the pic I uploaded -- in the course of troubleshooting an earlier and unrelated issue -- I set the DbType (highlighted row) to Int16. In the available selections I don't see an unsigned Int16 -- so, this appears to be signed---Annnnnnnnnnnnnnnnd, of course, good developers know Int16s hold values up to 32,767. Guess what happened when I changed it back to the default "Object"? Yup. It worked. So the problem not at all weird or strange. Instead, very much a rookie mistake.
All this said -- good learning experience. Additionally, #Albert D. Kallal and #fnostro you both gave me some good understanding on some things for the future. I appreciate both of you trying to help me. And, now I also, have a stackoverflow account :)
Thanks again.

Weird behavior when trying to update text in a GridView cell

I am trying to prepend some text to what's already in a GridView cell in the RowDataBound event:
protected void gvPatientSearch_RowDataBound(object sender, GridViewRowEventArgs e)
{
if (e.Row.RowType == DataControlRowType.DataRow)
{
DataRow dr = ((DataRowView)e.Row.DataItem).Row;
if (Convert.ToBoolean(dr["Confidential"]))
{
String name = String.Copy(e.Row.Cells[1].Text);
//the problem is the following line
e.Row.Cells[1].Text = "<b><font color='red'>!</font></b>" + name;
}
}
}
For some reason it seems that no matter what I do the original text is deleted. When I remove the line below the comment the name displays normally without the exclamation point; when I add the append code, for some reason the original text becomes a blank string and I only get the exclamation point. I have tried this with and without the String.Copy - I didn't think this would be needed but figured I would try it just in case. No luck.
I don't think this is relevant, but the first column in the row is a hidden column that contains a 1 or a 0. If the value is 1, I want to add the exclamation point. The data is there and this part is being called correctly, I just can't get the name to stay put.
Any ideas why this would be happening?
EDIT: Front end code below
<asp:GridView ID="gvPatientSearch" runat="server" Width="100%" CellPadding="4" ForeColor="#333333" GridLines="None" AllowPaging="True" AllowSorting="True"
PageSize="25" OnPageIndexChanging="gvPatientSearch_PageIndexChanging" OnSorting="gvPatientSearch_Sorting" OnRowDataBound="gvPatientSearch_RowDataBound"
AutoGenerateColumns="false" PagerSettings-Position="TopAndBottom" PagerStyle-HorizontalAlign="Right" PagerSettings-Mode="NumericFirstLast" PagerSettings-PageButtonCount="5"
PagerSettings-FirstPageText=" First " PagerSettings-LastPageText=" Last " PagerSettings-PreviousPageText=" Previous " PagerSettings-NextPageText=" Next ">
<AlternatingRowStyle BackColor="White" />
<EditRowStyle BackColor="#2461BF" />
<FooterStyle BackColor="#507CD1" Font-Bold="True" ForeColor="White" />
<HeaderStyle BackColor="#507CD1" Font-Bold="True" ForeColor="White" />
<PagerStyle BackColor="#2461BF" ForeColor="White" />
<RowStyle BackColor="#EFF3FB" />
<SelectedRowStyle BackColor="#D1DDF1" Font-Bold="True" ForeColor="#333333" />
<SortedAscendingCellStyle BackColor="#F5F7FB" />
<SortedAscendingHeaderStyle BackColor="#6D95E1" />
<SortedDescendingCellStyle BackColor="#E9EBEF" />
<SortedDescendingHeaderStyle BackColor="#4870BE" />
<Columns>
<asp:BoundField HeaderText="Confidential" DataField="Confidential" ItemStyle-CssClass="hiddencol" HeaderStyle-CssClass="hiddencol"></asp:BoundField>
<asp:HyperLinkField DataTextField="PatientName" DataNavigateUrlFields="PatientIdInternal" DataNavigateUrlFormatString="PatientProfile.aspx?InternalID={0}" HeaderText="Patient Name"
SortExpression="PatientName" />
<asp:BoundField DataField="PatientID" HeaderText="Patient ID" SortExpression="PatientID" />
<asp:BoundField DataField="AccountNumber" HeaderText="Account Number" SortExpression="AccountNumber" />
<asp:BoundField DataField="DateOfBirth" HeaderText="Date Of Birth" SortExpression="DateOfBirth" DataFormatString="{0:d}" />
<asp:BoundField DataField="PracticeName" HeaderText="Practice Name" SortExpression="PracticeName" />
<asp:BoundField DataField="PatientIdInternal" HeaderText="Internal ID" SortExpression="PatientIdInternal" Visible="false" />
</Columns>
</asp:GridView>
I can see the values of all the other fields showing up correctly in Visual Studio at this part of the code, only the name field that I am trying to modify shows as an empty string.
A HyperLinkField is rendered as a Hyperlink control, and for this reason you cannot retrieve the cell's text directly. If you want the text, you must retrieve it from the control, not the cell:
HyperLink myLink = e.Row.Cells[1].Controls[0] as HyperLink;
String name = myLink.text;
An alternative would be to grab the name directly from the datasource by doing DataBinder.Eval(e.Row.DataItem, "name") in your code-behind.
I don't know why that's happening, but I think you can work around it by applying you logic with a function like this:
public string Exclaim(bool confidential, string originalText)
{
if (confidential) {
return "<b><font color='red'>!</font></b>" + originalText;
} else {
return originalText;
}
}
In your gridview, invoke the function using:
<asp:TemplateField>
<ItemTemplate>
<%# Exclaim(Eval("Confidential"), Eval("Name"))%>
</ItemTemplate>
</asp:TemplateField>
I think that would work.
I went ahead and did it by changing the offending line to this:
e.Row.Cells[1].Text = "<b>font color='red'>!</font></b> " + Convert.ToString(dr["PatientName"]);
Still don't know why the other way doesn't work, if anyone else does and answers I will mark it correct.

Set radrating value for multiple items within Telerik RadGrid

I'm trying to put radrating control within RadGrid control for multiple items. This is what I have currently:
<telerik:RadGrid ID="RadGrid2" runat="server" OnItemDataBound="RadGrid2_ItemDataBound" OnNeedDataSource="RadGrid2_NeedDataSource">
<ClientSettings AllowDragToGroup="False">
</ClientSettings>
<MasterTableView>
<HeaderStyle Width="20px"></HeaderStyle>
</RowIndicatorColumn>
<Columns>
<telerik:GridBoundColumn DataField="Property.PropertyName" HeaderStyle-Width="100px" DataFormatString="{0:g}" HeaderText="Property" SortExpression="Property.PropertyName">
</telerik:GridBoundColumn>
<telerik:GridBoundColumn DataField="TestimonialHtml" DataFormatString="{0:g}" HeaderText="Review" SortExpression="TestimonialHtml">
</telerik:GridBoundColumn>
<telerik:GridBoundColumn DataField="TestimonialDate" DataFormatString="{0:g}" HeaderText="Review Date" SortExpression="TestimonialDate">
</telerik:GridBoundColumn>
<telerik:GridTemplateColumn HeaderText="Task" ItemStyle-Wrap="false">
<ItemTemplate>
<telerik:RadRating runat="server" ID="TestimonialRating" Value="RatingHelper" Precision="Half"></telerik:RadRating>
</ItemTemplate>
</telerik:GridTemplateColumn>
</Columns>
</MasterTableView>
</telerik:RadGrid>
While the gridboundcolumns are working fine, the radrating control doesn't want to accept the RatingHelper value and I'm getting this error:
Cannot create an object of type 'System.Decimal' from its string
representation 'RatingHelper' for the 'Value' property.
What should I change to make this work?
Take a look here: http://www.telerik.com/help/aspnet-ajax/grid-accessing-cells-and-rows.html. See how to access the rating in the OnItemDataBound event so you can set its value as needed. Direct binding in the markup is not going to work like this, as McGarnagle noted.
Another option is to use Eval() statements like shown here: http://demos.telerik.com/aspnet-ajax/rating/examples/gridrating/defaultcs.aspx.

RadGrid - get textbox in edit mode

I have an issue working with the telerik radgrid control. I am trying to use javascript to access a textbox when the grid is in edit mode.
My code looks like the following:
<telerik:RadGrid ID="RadGrid1" GridLines="None" runat="server" AllowAutomaticDeletes="True"
AllowSorting="False" AllowAutomaticInserts="True" PageSize="10" AllowAutomaticUpdates="True"
OnItemDataBound="RadGrid1_ItemDataBound" AllowMultiRowEdit="False" AllowPaging="False"
DataSourceID="DataSource1" OnItemUpdated="RadGrid1_ItemUpdated" AllowFilteringByColumn="False"
OnItemDeleted="RadGrid1_ItemDeleted" OnItemInserted="RadGrid1_ItemInserted" AutoGenerateColumns="false"
OnDataBound="RadGrid1_DataBound">
<PagerStyle Mode="NextPrevAndNumeric" />
<MasterTableView Width="100%" CommandItemDisplay="TopAndBottom" DataKeyNames="Id"
DataSourceID="DataSource1" HorizontalAlign="NotSet" EditMode="EditForms">
<Columns>
<telerik:GridEditCommandColumn ButtonType="ImageButton" UniqueName="EditCommandColumn">
<ItemStyle CssClass="MyImageButton" />
</telerik:GridEditCommandColumn>
<telerik:GridButtonColumn ConfirmText="Delete this product?" ConfirmDialogType="RadWindow"
ConfirmTitle="Delete" ButtonType="ImageButton" CommandName="Delete" Text="Delete"
UniqueName="DeleteColumn">
<ItemStyle HorizontalAlign="Center" CssClass="MyImageButton" />
</telerik:GridButtonColumn>
<telerik:GridBoundColumn DataField="Id" HeaderText="Id" Display="false" ReadOnly="true" />
<telerik:GridBoundColumn DataField="Manufacturer" HeaderText="Manufacturer" />
<telerik:GridBoundColumn DataField="Description" HeaderText="Description" />
<telerik:GridBoundColumn DataField="Configuration" HeaderText="Configuration" />
<telerik:GridDropDownColumn DataField="TypeId" HeaderText="Type" UniqueName="PartsType"
DataSourceID="PartsTypeDataSource" ListTextField="Name" ListValueField="Id" />
What I am after is that, during edit mode, when the user selects a certain value from the dropdown list 'PartsType', one of the other fields - eg 'Manufacturer' will be shown/hide.
I could get the dropdown value (in javascript) by attaching a javascript function to the dropdownlist:
function PartsTypeIndexChanged(sender, args) {
var selectedValue = args.get_item()._text;
}
I just dont know which method to use to get the 'Manufacturer' field, so I can show/hide it.
Could anyone please help?
Many thanks.
A possible approach could be to use RadControls client-side static API
$telerik.findElement(gridDOMElement, "Manufacturer");
This will help you access the column editor - I suppose it is ASP.NET TextBox rendered as input. For numeric or date columns the editor will probably be Telerik client component so you have to use findControl instead of findElement.
More info here:
http://www.telerik.com/help/aspnet-ajax/telerik-static-client-library.html
Good luck
Please check below link.
http://www.telerik.com/community/forums/aspnet-ajax/grid/set-controls-attribute-like-enable-disable-on-insert-edit-mode-using-jquery.aspx

css problem in top:?

i have to fix the header in a gridview and i use this in style Class
<style type="text/css">
.gridFixedHeader
{
background-color:white;
position:relative;
top:expression(GridView1.offsetParent.scrollTop-2);
}
</style>
but i get an error that expression(GridView1.offsetParent.scrollTop-2);is not valid...
what all do i need to do to make this work.....
any suggestions
Main aim... to fix the headers so they dont move when the gridview is scrolled up or down...
any help will be appreciated...
here is my gridview code
<asp:Panel ID="Panel1" runat="server" Height="100px" ScrollBars="Vertical">
<asp:GridView ID="GridView1" runat="server" AllowSorting="True"
AutoGenerateColumns="False" BackColor="White" BorderColor="#CCCCCC"
BorderStyle="None" BorderWidth="1px" CellPadding="3"
DataKeyNames="MachineGroupID" DataSourceID="SqlDataSource1">
<RowStyle ForeColor="#000066" />
<HeaderStyle CssClass="gridFixedHeader" />
<Columns>
<asp:BoundField DataField="MachineGroupID" HeaderText="MachineGroupID"
InsertVisible="False" ReadOnly="True" SortExpression="MachineGroupID" />
<asp:BoundField DataField="MachineGroupName" HeaderText="MachineGroupName"
SortExpression="MachineGroupName" />
</Columns>
<FooterStyle BackColor="White" ForeColor="#000066" />
<PagerStyle BackColor="White" ForeColor="#000066" HorizontalAlign="Left" />
<SelectedRowStyle BackColor="#669999" Font-Bold="True" ForeColor="White" />
<HeaderStyle BackColor="#006699" Font-Bold="True" ForeColor="White" />
</asp:GridView>
</asp:Panel>
so here i have a gridview where when i scroll the header row moves too.. i dont want that to happen..
It is not valid in W3C. It is an IE only thing. To do what you are looking for in a valid way would require you to run some JavaScript and fix your headers.
If you explain your desired outcome I am sure someone can help. I have made GridView headers look exactly like I want many times.
UPDATE: Here is a good article: http://www.dotnetcurry.com/ShowArticle.aspx?ID=255
When the gridview is rendered to html, the GridView1 ID is probably being rewritten.
you probably want something like:
top:expression(<%= GridView1.ClientID %>.offsetParent.scrollTop-2);
although this may get you what you want it's probably not the best form.
You are heavily advised against using CSS expressions, as they get executed on every event of the browser - including mouseMove. They also don't work on anything but IE.
I can't answer your question further due to lack of details of what you're trying to achieve.
If you're trying to fix it to the top of the viewport try:
.gridFixedHeader
{
background-color:white;
position:fixed;
top:20px; //optional
}
in the elements CSS
edit: just realised you look like you're styling a GridViews header so this will probably not work, try posting some of the Gridview generated HTML and what yo want done with it please

Categories