Yesterday’s momentary dilemma of the day was being able to enable and with that disable links in an ASP.NET datagrid control. It was a fairly easy task, just took a little time to find what I needed to make it work. So here is what we’re looking for:

DataGrid

Quite simple by the look of it, so let’s get under the hood and pick apart how it works. To start we’ll look at the way I would normally tackle a regular datagrid with a delete button on it. Keep in mind that the delete button is the only thing on the datagrid so I am just using the Select command, if I were to implement both it would look a little different on the delete button, but there are plenty of articles out there to show how to set that up.

<asp :datagrid id=dgInstructorTravel runat="server" AutoGenerateColumns="False">
<columns>
<asp :buttoncolumn Text="Delete" HeaderText=" " CommandName="Select"></asp>
<asp :boundcolumn DataField="InstructorTravelID" Visible="False"></asp>
<asp :boundcolumn DataField="ItemDate" HeaderText="Date"></asp>
<asp :boundcolumn DataField="TravelItem" HeaderText="Travel Item"></asp>
<asp :boundcolumn DataField="Cost" HeaderText="Cost"></asp>
<asp :boundcolumn DataField="RequestLineItem" Visible="False"></asp>
</columns>
</asp>

So normally I would just set up a button column and go from there and the other columns (the last one that has it’s visible field set to false will mostly be for use in the upcoming change I need to make in order to disable that Delete button). Of course you don’t have to take the time to set up your columns in the asp file, but I like to because it gives me a little more control over what shows up on the screen and makes it easier to use the same dataset for multiple things. So the code behind that is simply just filling up a DataSet Object and binding it to the datagrid. That isn’t really necessary for this post but I know I get annoyed when people just say “just databind a dataset to the datagrid” and I reply I would if you would show me how. So here goes:

Dim dt As New DataTable
dt.Columns.Add(New DataColumn(“InstructorTravelID”))
dt.Columns.Add(New DataColumn(“TravelItem”))
dt.Columns.Add(New DataColumn(“ItemDate”))
dt.Columns.Add(New DataColumn(“Cost”))
dt.Columns.Add(New DataColumn(“RequestLineItem”))
RSet = cmd.ExecuteReader()
While RSet.Read()
Dim dr As DataRow = dt.NewRow()
dr(0) = RSet(“InstructorTravelID”)
dr(1) = RSet(“TravelItem”)
dr(2) = FormatDateTime(RSet(“ItemDate”), DateFormat.ShortDate)
dr(3) = RSet(“Cost”)
dr(4) = RSet(“RequestLineItem”)
dt.Rows.Add(dr)
End While
dgInstructorTravel.DataSource = dt
dgInstructorTravel.DataBind()

One thing to note, normally you don’t even have to go so far as to create the DataTable and set up all the columns, but that was the only way I could find to format the Date after the fact so I just went with that way. So now that we have all of our data in the datagrid there is really only one thing to change in the earlier DataGrid definition, and that is to replace the button column with a template column like this:

<asp :templatecolumn>
<headertemplate></headertemplate>
<itemtemplate>
<asp :linkbutton ID=”lnkInstructorTravelDelete” Runat=”server” CommandName=”Delete” OnClick=”deleteRequest”
CommandArgument=’<%#DataBinder.Eval(Container.DataItem, "InstructorTravelID")%>’
Enabled=’< %#IIf(DataBinder.Eval(Container.DataItem, “RequestLineItem”) is DBNull.Value, “True”,
“False”)%>’>Delete</asp>
</itemtemplate>
</asp>

So first and most important that you might not catch, I changed my mind at this point and decided to use the Delete Command, just in case later on someone wanted me to drop a Select on it. If you leave the CommandName=”Select” like it was before then it will just run off the old SelectIndexChanged Method that you had before. The OnClick=”deleteRequest” just means that it calls a method deleteRequest from the CodeBehind page. The command argument is passed, but by the title of the article you came for the Enabled section.

What I am doing there is putting an IIf (If and Only If) the RequestLineItem is Null, then set enabled to True, otherwise set it to False. One important thing to remember though is that in VB IIf will evaluate both outcomes, so if you put functions in there know that it will try to run both of them. It’s rather annoying especially if you are doing something like passing what could be a null or nothing object so keep that in the back of your mind.

So lastly, I’ll throw up the essentials of my deleteRequest method, just to make sure you have everything you need to accomplish this:

Public Sub deleteRequest(ByVal sender As Object, ByVal e As System.EventArgs)
Dim lnk As LinkButton
lnk = CType(sender, LinkButton)
Response.Write(lnk.CommandArgument)
End Sub

Questions? Ways to do it better? Leave a comment.

EDIT: Having problems with my formatter when it comes to the asp.net, so sorry in advance for that. If you notice things like asp:datagrid are turning into asp :datagrid and the closing tags are losing their attributes so please keep that in mind while I try to correct the problem.

c5767a87465c3006b31045887cb963c1->


One Response to “Enabling/Disabling Links in a DataGrid”  

  1. 1 Nathanael

    Hmm looks interesting. Personally, I’ve never used DataGrids – still clutching onto my ASP ways I guess in that regard. I’m not willing to trust it yet – but maybe I should have a play around with it. But so far, custom classes with internal arrays and stuff do the trick for me.

    How do DataGrids fit in with dOOdads?

Leave a Reply