UserControl inside DataList - asp.net

I have a UserControl inside DataList, I fill the controls inside the usercontrol according to the PrimeryKey of the DataList's data. At first load program behaves as expected but when user changes page index all the MessageID's returns 0, most probably value coming with
<%# Eval("id").toString()%> is lost. I dont want to hard code the usercontrol because i used it in many place in the project, it makes the code maintainable. How can i correct this behaviour? Thanks in advance.
My code is below:
<asp:DataList ID="DataList1" runat="server" Width="658px">
<ItemTemplate>
<table style="width: 100%;">
<tr>
<td style="font-weight: 700; color: #FF0000; font-size: medium; font-size: 10pt; font-family: Tahoma">
<%# Eval("hadding") +" ["+Eval("startTime")+" - "+Eval("endTime")+"]"%>
</td>
</tr>
<tr>
<td style="font-weight: 700; font-size: 10pt; font-family: Tahoma">
<%# Eval("location") %>
</td>
</tr>
<tr>
<td>
<uc1:MyUserControl ID="MyUserControl1" runat="server" MessageID='<%# Eval("id").toString()%>' />
</td>
</tr>
</table>
</ItemTemplate>
</asp:DataList>
<table>
<tr>
<td>
<asp:Button ID="btnfirst" runat="server" Font-Bold="true" Text="<<" Height="31px"
Width="43px" OnClick="btnfirst_Click" /></td>
<td>
<asp:Button ID="btnprevious" runat="server" Font-Bold="true" Text="<" Height="31px"
Width="43px" OnClick="btnprevious_Click" /></td>
<td>
<asp:Button ID="btnnext" runat="server" Font-Bold="true" Text=">" Height="31px"
Width="43px" OnClick="btnnext_Click" /></td>
<td>
<asp:Button ID="btnlast" runat="server" Font-Bold="true" Text=">>" Height="31px"
Width="43px" OnClick="btnlast_Click" /></td>
</tr>
</table>
and my user control:
Partial Class MyUserControl
Inherits System.Web.UI.UserControl
Private _messageID As Integer
Protected Sub Page_Load(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load
If (_messageID > 0) Then
Fill(_messageID)
End If
End Sub
Public Property MessageID As Integer
Get
Return _messageID
End Get
Set(value As Integer)
_messageID = value
End Set
End Property
Protected Sub Fill(messageID As Integer)
'Some code
End Sub
End Class

Difficult to answer without looking at the whole page lifecycle, but you may try to store the MessageId in your control's ViewState, like this :
Public Property MessageID As Integer
Get
If (Me.ViewState("VSMessageID") IsNot Nothing) Then
return CType(Me.ViewState("VSMessageID "), Integer)
else
return 0 // arbitrary value
End Get
Set(value As Integer)
Me.ViewState.Add("VSMessageID", value)
End Set
End Property
Then :
Protected Sub Page_Load(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load
If (MessageID > 0) Then
Fill(MessageID )
End If
End Sub
See http://msdn.microsoft.com/en-us/library/ms227551%28v=vs.85%29.aspx?cs-save-lang=1&cs-lang=vb#code-snippet-1
Sorry if bad VB.Net syntax

I solved the problem by changing the usercontrol as such:
Partial Class MyUserControl
Inherits System.Web.UI.UserControl
Public Property MessageID As Integer
Get
Return 0
End Get
Set(value As Integer)
Fill(value)
End Set
End Property
Protected Sub Fill(messageID As Integer)
'Some code
End Sub
End Class
As jbl said, this is because of the page lifecycle. OnPageIndexChange event of an ASPxDataview or on your custom PageIndexChange event for asp.net DataList, code work as such:
DataList (or ASPxDataview ) Load
UserControl Property setting
UserControl Load
PageIndexChange event
UserControl Load
UserControl Property setting
That's why on UserControl.Load Property is not set.

Related

Pass Text From a List View Controller to a OnClick Sub VB.Net

Is there a way to pass text from a List View controller to a OnClick Subroutine? For example, there's a label in the List View and I've attached a Button in the List View and attached an OnClick Subroutine to it. Now I want to pass the text from the Label over to the OnClick Subroutine. I hope this make sense. Down below is my code:
VB.Net Code:
Protected Sub AmButtonClick(ByVal sender As Object, ByVal e As System.EventArgs)
Dim url As String = CType(Me.AmListViewDetails.FindControl("merchantLink"), Label).Text
Dim sb As New StringBuilder()
sb.Append("<script type = 'text/javascript'>"_
sb.Append("window.open('")
sb.Append(url)
sb.Append("');")
sb.Append("</script>")
ClientScript.RegisterStartupScript(Me.GetType(), "script", sb.ToString())
End Sub
ASP.Net:
<asp:ListView runtat="server" ID="AmListViewDetails" ...>
<ItemTemplate>
<table runat="server">
<tr runat="server">
<td runat="server">
<asp:Label ID="merchantLink" runat="server" Text='<%Eval("Link")%>' />
</td>
</tr>
<tr runat="server">
<td runat="server">
<asp:Button ID="AmBtn" runat="server" Text="Checkout" OnClick="AmButtonClick"/>
</td>
</tr>
</table>
</ItemTemplate>
</asp:ListView>
Add a CommandArgument property to the button. That's going to be the value passed to the event handler. You don't need an OnClick property.
<asp:Button ID="AmBtn" runat="server" Text="Checkout" CommandArgument="???" />
Your event handler would be
Sub AmListViewDetails_ItemCommand(object sender, ListViewCommandEventArgs e)
Dim valuePassedFromListView = Cstr(e.CommandArgument)
End Sub

Update panel automatically clears textboxes

I'm trying to combine an event of automatic printing of messages in case the passwords will not match. For that purpose I'm using an Update panel.
The Error message prints perfectly My problem is that both text-boxes automatically created after it. even thought I don't specify it in the code. I can't understand what have I done wrong.
This is the code for front end:
<asp:TextBox ID="NonPass1" runat="server" TextMode="Password"></asp:TextBox>
<asp:TextBox ID="NonPass2" runat="server" TextMode="Password" autopostback="True"></asp:TextBox>
<asp:UpdatePanel ID="UpdatePanel6" runat="server">
<ContentTemplate>
<asp:Panel ID="Panel6" runat="server">
<asp:Label ID="Label1" class="errorMess" runat="server" Text="The Passwords do not match!!!"></asp:Label>
</asp:Panel>
</ContentTemplate>
<Triggers>
<asp:AsyncPostBackTrigger ControlID="NonPass2" EventName="TextChanged" />
</Triggers>
</asp:UpdatePanel>
this is the back end code(I'm using VB):
Protected Sub NonPass2_TextChanged(ByVal sender As Object, ByVal e As EventArgs) Handles NonPass2.TextChanged
If NonPass1.Text <> NonPass2.Text Then
Panel3.Visible = False
Panel6.Visible = True
Else
Panel3.Visible = False
Panel6.Visible = False
End If
End Sub
maybe you can use javascript functions.
<script>
var t1 = false; // textbox1 onfocus triggered = true;
var t2 = false; // textbox2 onfocus triggered = true;
function clearTBox() {
if (t1 && t2) {
if (document.getElementById("textbox1Name").value != document.getElementById("textbox1Name2").value) {
alert("Insert your code here");
}
}
}
</script>
Heres what i use in c# for this, maybe you can inherit the technique
private void ClearTextBoxes()
{
Action<Control.ControlCollection> func = null;
func = (controls) =>
{
foreach (Control control in controls)
if (control is TextBox)
(control as TextBox).Clear();
else
func(control.Controls);
};
func(Controls);
}
then call cleartextboxes();
Hope that helped :)
what do you mean :
My problem is that both text-boxes automatically created after it
please, make your question more clearance
Try not to use updatepanel,
try this
<asp:TextBox ID="NonPass1" runat="server" TextMode="Password"></asp:TextBox>
<asp:TextBox ID="NonPass2" runat="server" TextMode="Password" autopostback="True"></asp:TextBox>
<div id="Div_Error" runat="server" visible="false" style="width:100%">
<asp:Label ID="Label1" class="errorMess" runat="server" Text="The Passwords do not match!!!"></asp:Label>
and use this in the code behind:
Protected Sub NonPass2_TextChanged(ByVal sender As Object, ByVal e As EventArgs) Handles NonPass2.TextChanged
If NonPass1.Text <> NonPass2.Text Then
Div_Error.visible=true;
Else
Div_Error.visible=false;
End If
End Sub
The only logical reason for the behavior as you described is perhaps, you put the above password boxes inside another UpdatePanel.
Therefore, the password boxes will be reloaded on postbacks (textchanged event), and TextBox of type Password do not retain its value after postbacks for security reason.
Though, if security is not a concern for you, there is a workaround to 'avoid' the password textboxes from being cleared on postbacks, by reassigning their values every time postbacks occur. Just include the following codes in the page Load event.
Protected Sub Page_Load(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load
NonPass1.Attributes.Add("value", NonPass1.Text)
NonPass2.Attributes.Add("value", NonPass2.Text)
End Sub
this is a simple example:
<table class="mytable" cellspacing="0" style="width: 100%">
<tr>
<td>
<asp:TextBox ID="Txt_Pass" runat="server" ></asp:TextBox>
</td>
<td>
<asp:TextBox ID="Txt_Re_Pass" runat="server" ></asp:TextBox>
</td>
<td width="66%" align="left">
<asp:Button ID="Btn_Filter" runat="server" Text="" Height="22px" />
</td>
</tr>
</table>
<br />
<div id="Div_Error" runat="server" visible="false" style="width:100%">
<asp:Label ID="lbl_Error" runat="server" class="msg">
</asp:Label>
</div>
and in the code behind , use this:
Protected Sub Btn_Filter_Click(ByVal sender As Object, ByVal e As System.EventArgs) Handles Btn_Filter.Click
If Trim(Txt_Re_Pass.Text) <> "" Then
Div_Error.Visible = False
if Txt_Pass.Text <> Txt_Re_Pass.Text then
Div_Error.Visible = True
lbl_Error.text="The Passwords do not match!!!""
else
Div_Error.Visible = False
End if
Else
Div_Error.Visible = True
lbl_Error.text="Please re enter your password"
End If
End Sub

How to do Paging in a Datalist control?

I have my DataList in ASP.NET 3.5 Access 2003 DataSource. I want to create paging for a DataList control using VB.
DataList lacks functionality of pagging like in GridView but its possible to implement pagging functionality for DataList.
Here i have done pagging using PagedDataSource which enclose the paging related properties of a data-bound control, that allow it to perform the pagging. More details about PagedDataSource
Inline code
<div>
<asp:DataList ID="dataListStudent" runat="server">
<ItemTemplate>
<table cellpadding="10">
<tr>
<td nowrap="nowrap">
<b>Student id</b>
</td>
<td nowrap="nowrap">
<b>First name</b>
</td>
<td nowrap="nowrap">
<b>Last name</b>
</td>
<td>
<b>City</b>
</td>
</tr>
<hr />
<tr>
<td nowrap="nowrap">
<%# Eval("StudentID") %>
</td>
<td nowrap="nowrap">
<%# Eval("FirstName") %>
</td>
<td nowrap="nowrap">
<%# Eval("LastName") %>
</td>
<td nowrap="nowrap">
<%# Eval("City") %>
</td>
</tr>
</table>
</ItemTemplate>
</asp:DataList>
<br />
<table border="0" width="410">
<tr>
<td align="left">
<asp:LinkButton ID="lbPrev" runat="server">
Prev
</asp:LinkButton>
</td>
<td align="right">
<asp:LinkButton ID="lbNext" runat="server">
Next
</asp:LinkButton>
</td>
</tr>
</table>
</div>
Code-behind
Imports System.Data
Imports System.Data.OleDb
Partial Class _Default
Inherits System.Web.UI.Page
Dim pageds As New PagedDataSource()
Public Property CurrentPage() As Integer
Get
If Me.ViewState("CurrentPage") Is Nothing Then
Return 0
Else
Return Convert.ToInt16(Me.ViewState("CurrentPage").ToString())
End If
End Get
Set(ByVal value As Integer)
Me.ViewState("CurrentPage") = value
End Set
End Property
Sub bindDataList()
Dim sql As String
sql = "SELECT * FROM STUDENTS"
Dim da As New OleDbDataAdapter(sql, "Provider=Microsoft.Jet.OLEDB.4.0;Data Source=|DataDirectory|\Course.mdb")
Dim dt = New DataTable()
da.Fill(dt)
Try
pageds.DataSource = dt.DefaultView
pageds.AllowPaging = True
pageds.PageSize = 3
pageds.CurrentPageIndex = CurrentPage
lbNext.Enabled = Not pageds.IsLastPage
lbPrev.Enabled = Not pageds.IsFirstPage
dataListStudent.DataSource = pageds
dataListStudent.DataBind()
Catch ex As Exception
Throw ex
End Try
End Sub
Protected Sub lbPrev_Click(ByVal sender As Object, ByVal e As System.EventArgs) Handles lbPrev.Click
currentPage -= 1
bindDataList()
End Sub
Protected Sub lbNext_Click(ByVal sender As Object, ByVal e As System.EventArgs) Handles lbNext.Click
currentPage += 1
bindDataList()
End Sub
Protected Sub Page_Load(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load
If Not IsPostBack Then
bindDataList()
End If
End Sub
End Class
Your connection string, Column names might be different you might want different layout of DataList feel free to fiddle with it. Hopefully it will help you to solve the problem.

Getting the 'Object reference not set to an instance of an object' error..vb

I don't undertand why I'm getting this error, code was working and running perfectly earlier. I was trying to update the user's email via button. It worked fine but now for some reason it keeps giving me the error:
"Object reference not set to an instance of an object.
Line 34: EmailTextBox.Text = u.Email"
Been scratching at this for a couple of hours now, anyone have an idea what it might be?
My aspx.vb code is:
Public Class _Default
Inherits System.Web.UI.Page
Dim u As MembershipUser
Protected Sub Page_Load(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load
u = Membership.GetUser(User.Identity.Name)
If Not IsPostBack Then
EmailTextBox.Text = u.Email
End If
End Sub
Public Sub UpdateEmailButton_OnClick(ByVal sender As Object, ByVal args As EventArgs)
Try
u.Email = EmailTextBox.Text
Membership.UpdateUser(u)
Msg.Text = "User e-mail updated."
Catch e As System.Configuration.Provider.ProviderException
Msg.Text = e.Message
End Try
End Sub
aspx code:
<h3>Update E-Mail Address for <%=User.Identity.Name%></h3>
<asp:Label id="Msg" ForeColor="maroon" runat="server" /><br />
<table cellpadding="3" border="0">
<tr>
<td>E-mail Address:</td>
<td><asp:TextBox id="EmailTextBox" MaxLength="128" Columns="30" runat="server" /></td>
<td><asp:RequiredFieldValidator id="EmailRequiredValidator" runat="server"
ControlToValidate="EmailTextBox" ForeColor="red"
Display="Static" ErrorMessage="Required" /></td>
</tr>
<tr>
<td></td>
<td><asp:Button id="UpdateEmailButton"
Text="Update E-mail"
OnClick="UpdateEmailButton_OnClick"
runat="server" /></td>
</tr>
</table>
you need into to the debugging model and see the u = Membership.GetUser(User.Identity.Name) whether is null.
i guess the Membership.GetUser(User.Identity.Name) return null. may be your logged was timeout,may be just MembershipUser occure error.

RadListView insertitemtemplate still showing after insert

I have a pretty simple scenario using manual data operations with rad list view. I insert an item into my collection in the ItemInserting event, the listview shows the new item but the insertitemtemplate is still showing. Is my setup wrong? Do I have to manually hide the thing?
Markup
<%# Page Language="VB" AutoEventWireup="false" CodeFile="Test2.aspx.vb" Inherits="Test2" %>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head runat="server">
<title></title>
</head>
<body>
<form id="form1" runat="server">
<telerik:RadScriptManager runat="server" ID="rsm"></telerik:RadScriptManager>
<div>
<telerik:RadListView ID="rlv" runat="server" DataKeyNames="UserID" ItemPlaceholderID="itemPlaceholder" Height="400px" AllowPaging="true">
<InsertItemTemplate>
<tr>
<td>
<div style="vertical-align: middle; white-space: nowrap;">
<asp:LinkButton ID="btnInsert2" runat="server" Text="Insert" CommandName='<%# Telerik.Web.UI.RadListView.PerformInsertCommandName %>'></asp:LinkButton>
<asp:LinkButton ID="btnCancel2" runat="server" Text="Cancel" CommandName='<%# Telerik.Web.UI.RadListView.CancelCommandName %>'></asp:LinkButton>
</div>
</td>
<td>
<div style="vertical-align: middle; white-space: nowrap;">
<telerik:RadComboBox id="RadComboBox1" runat="server" autopostback="True" causesvalidation="False" allowcustomtext="True" backcolor="White" emptymessage="Select a Person" enableloadondemand="True" showmoreresultsbox="True" width="150px" dropdownwidth="200px" zindex="9002" enablescreenboundarydetection="False" style="margin-bottom: 0px" datatextfield="UserName" datavaluefield="pkUserID" filter="Contains" onitemsrequested="RCB_ItemsRequested">
<CollapseAnimation Duration="200" Type="OutQuint" />
</telerik:RadComboBox>
</div>
</td>
</tr>
</InsertItemTemplate>
<ItemTemplate>
<tr>
<td>
<asp:Literal ID="lName" runat="server" Text='<%# Eval("UserName") %>'></asp:Literal>
</td>
</tr>
</ItemTemplate>
<LayoutTemplate>
<asp:LinkButton ID="btnInsert" runat="server" CausesValidation="False" CommandName='<%# Telerik.Web.UI.RadListView.InitInsertCommandName %>' Text="Add User" />
<table>
<tr>
<td style="border: ridge 1px lightgray">
<strong>Applicable Users</strong>
<table>
<asp:PlaceHolder runat="server" ID="itemPlaceholder"></asp:PlaceHolder>
</table>
</td>
</tr>
</table>
</LayoutTemplate>
</telerik:RadListView>
</div>
</form>
</body>
</html>
Code Behind
Partial Class Test2
Inherits System.Web.UI.Page
Public Property Users As IList(Of UserInfo)
Get
Return If(ViewState("Users"), New List(Of UserInfo))
End Get
Set(ByVal value As IList(Of UserInfo))
ViewState("Users") = value
End Set
End Property
Protected Sub Page_Load(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load
If Not Page.IsPostBack Then
Me.Users = GetInitialUsers()
End If
rlv.DataSource = Users
rlv.DataBind()
Me.ViewState.SetItemDirty("Users", True)
End Sub
Private Function GetInitialUsers() As IList(Of UserInfo)
Dim Users As New List(Of UserInfo)
Users.Add(New UserInfo(1, "1"))
Users.Add(New UserInfo(2, "2"))
Users.Add(New UserInfo(3, "2"))
Users.Add(New UserInfo(4, "4"))
Return Users
End Function
Protected Sub RCB_ItemsRequested(ByVal sender As Object, ByVal e As Telerik.Web.UI.RadComboBoxItemsRequestedEventArgs)
Dim ComboBox As Telerik.Web.UI.RadComboBox = sender
Dim itemOffset As Integer = e.NumberOfItems
Dim NumberOfItems As Integer = 1000000000
Dim Take As Integer = 20
For i As Integer = 0 To Take
ComboBox.Items.Add(New Telerik.Web.UI.RadComboBoxItem(i + itemOffset, (i + itemOffset).ToString))
Next
Dim NumberOfItemsInComboBox As Integer = e.NumberOfItems + ComboBox.Items.Count
If NumberOfItems > 0 Then
e.Message = [String].Format("Items <b>1</b>-<b>{0}</b> out of <b>{1}</b>", NumberOfItemsInComboBox, NumberOfItems)
Else
e.Message = "No matches"
End If
e.EndOfItems = (NumberOfItemsInComboBox >= NumberOfItems)
End Sub
Protected Sub rlv_ItemInserting(ByVal sender As Object, ByVal e As Telerik.Web.UI.RadListViewCommandEventArgs) Handles rlv.ItemInserting
Dim ComboBox As Telerik.Web.UI.RadComboBox = e.ListViewItem.FindControl("RadComboBox1")
If Not String.IsNullOrWhiteSpace(ComboBox.SelectedValue) Then
Dim UserID As Integer = ComboBox.SelectedValue
Dim UserName As String = ComboBox.Text
Me.Users.Add(New UserInfo(UserID, UserName))
Else
e.Canceled = True
End If
End Sub
<Serializable()>
Public Class UserInfo
Private _UserID As Integer
Private _UserName As String
Public ReadOnly Property UserID As Integer
Get
Return _UserID
End Get
End Property
Public ReadOnly Property UserName As String
Get
Return _UserName
End Get
End Property
Public Sub New(ByVal UserID As Integer, ByVal UserName As String)
_UserID = UserID
_UserName = UserName
End Sub
End Class
End Class
After you have inserted the new item, set the InsertItemPosition to None:
RadListView1.InsertItemPosition = RadListViewInsertItemPosition.None
radlistview1.IsItemInserted=false;
or set e.canceled=false after save click

Resources