Visual Studio Have to Click Button Twice - asp.net

I'm trying to write code that will, at the click of a button, push a string variable onto a page and then open that page. The trouble that I am running into is that variable, a button's text, is nested within a gridview, making accessing it difficult. It is also difficult because I am importing it from an SQL database into the Gridview, so I cannot access it directly from there either. It works with my current code if I use the button's onClick event, but then for some reason I have to click the button twice in order for it to work. I have read on here to instead use the onPreRender event, but that interferes with pushing the string variable onto the page, and I can't have that. Is there any other way to get rid of having to click the button twice that doesn't involve the onPreRender event?
Here is the code:
Imports System.Data.SqlClient
Imports System.IO
Partial Class PartsLookup
Inherits System.Web.UI.Page
Protected Sub Page_Load(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load
End Sub
Private Function FindControlRecursive(ByVal RootControl As Control, ByVal ControlID As String) As Control
If RootControl.ID = ControlID Then
Return RootControl
End If
For Each controlToSearch As Control In RootControl.Controls
Dim controlToReturn As Control = FindControlRecursive(controlToSearch, ControlID)
If controlToReturn IsNot Nothing Then
Return controlToReturn
End If
Next
Return Nothing
End Function
Protected Sub Button1Click(ByVal sender As Object, ByVal e As System.EventArgs)
Dim clickedButton As Button = sender
MsgBox(clickedButton.Text)
Dim ControlText As Control = FindControlRecursive(GridView1, clickedButton.ID)
Dim ControlText1 As Button = ControlText
Dim MachineNumber As String = ControlText1.Text
If MachineNumber = "" Then
ControlText1.Visible = False
End If
Dim SpecificPart() As String = {String that is the files contents, the middle of which is where the variable will be pushed to}
Dim path As String = "File path where the variable is to be pushed to"
File.WriteAllLines(path, SpecificPart)
clickedButton.PostBackUrl = "~/PartNumberPages/PartTemplate.aspx"
End Sub
End Class

Related

Gridview rowcommand event not firing in dynamically added usercontrol

I have a usercontrol with gridview and rowcommand event.
This usercontrol is added dynamically using LoadControl on a button click of a page. The gridview's rowcommand doesn't fire.
Here is the code that loads the usercontrol on button click:
Protected Sub btnSearch_Click(ByVal sender As Object, ByVal e As EventArgs) Handles btnSearch.Click
'<ucTitle:SearchList ID="ucSearchList" runat="server" Visible="false" />
Dim ucSearchList As TitleSearchList = LoadControl("~/Controls/TitleSearchList.ascx")
ucSearchList.ISBN = txtSearchISBN.Text
ucSearchList.LoadTitleSearchList()
pnlSearchResults.Controls.Add(ucSearchList)
End Sub
And here is the code in usercontrol
Public Class TitleSearchList
Inherits System.Web.UI.UserControl
Public Property ISBN As String
Protected Sub Page_Load(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load
If Not IsPostBack Then
LoadTitleSearchList()
End If
End Sub
Public Sub LoadTitleSearchList()
Dim _isbn As String = ISBN
Dim titles As New List(Of Title)
titles = New List(Of Title) From {
New Title With {.ISBN = _isbn, .TitleName = "Title check"},
New Title With {.ISBN = _isbn, .TitleName = "Title check"},
New Title With {.ISBN = _isbn, .TitleName = "Title check"},
New Title With {.ISBN = _isbn, .TitleName = "Title check"}
}
gvTitle.DataSource = titles
gvTitle.DataBind()
End Sub
Public Sub gvTitle_Rowcommand(ByVal sender As Object, ByVal e As GridViewCommandEventArgs) Handles gvTitle.RowCommand
If e.CommandName = "TitleDetail" Then
Response.Redirect("TitleSearch.aspx?isbn=" & e.CommandArgument().ToString())
End If
End Sub
End Class
Events in GridViews that are added dynamically in a UserControl get a little ugly. Since UserControls that are added dynamically have to be re-added on the post-back, you have to rebind the GridView DataSource, which makes you lose out on automatically getting those Events fired for you. That being said, you can still pull it off with some parsing of the __EVENTTARGET of the Form.
Add a HiddenField that tells you whether or not you need to re-add the UserControl. Add this in your Page_Load Event Handler:
If CBool(hdnTitleSearchActive.Value) = True Then
AddSearchListToPanel()
End If
Call AddSearchListToPanel() in your btnSearch_Click Event Handler.
Now this implementation of AddSearchListToPanel can be cleaned up some, but this should be good enough to get you going. Note that the Button triggering the GridView Command in my example has the ID of lbtTest. You will have to adjust based on the ID that you are using.
Private Sub AddSearchListToPanel()
Dim ucSearchList As TitleSearchList = LoadControl("~/Controls/TitleSearchList.ascx")
ucSearchList.ISBN = txtSearchISBN.Text
ucSearchList.LoadTitleSearchList()
pnlSearchResults.Controls.Add(ucSearchList)
hdnTitleSearchActive.Value = True
Dim strEventTarget As String = HttpContext.Current.Request.Form("__EVENTTARGET")
If Not strEventTarget Is Nothing AndAlso strEventTarget.Contains("gvTitle$") AndAlso _
strEventTarget.Contains("$lbtTest") Then
'Value example = gvTitle$ctl02$lbtTest
Dim intRowNumber As Integer = (CInt(strEventTarget.Substring(11, 2)) - 1)
Dim lbtCommandSource As LinkButton = CType(CType(ucSearchList.FindControl("gvTitle"), GridView).Rows(intRowNumber).FindControl("lbtTest"), LinkButton)
Dim objCommandEventArguments As New CommandEventArgs(lbtCommandSource.CommandName, lbtCommandSource.CommandArgument)
Dim objGridViewCommandEventArgs As New GridViewCommandEventArgs(lbtCommandSource, objCommandEventArguments)
ucSearchList.gvTitle_Rowcommand(lbtCommandSource, objGridViewCommandEventArgs)
End If
End Sub

Object reference not set to an instance of an object in ASP(vb)

I came across to this code that creates control dynamically. I tried it. However, whenever I run it, Object reference not set to an instance of an object error pops out and points out to a certain line in the code( i put ---> on the line). I'm a newbie in this programming language. I don't know what to do.
Here's the code I got:
Imports System.Collections.Generic
'Imports System.Data.Odbc
Partial Public Class main
Inherits System.Web.UI.Page
Private controlCounter As Integer = 0
Private myControlList As List(Of String)
Protected Overrides Sub LoadViewState(ByVal savedState As Object)
MyBase.LoadViewState(savedState)
myControlList = DirectCast(ViewState("myControlList"), List(Of String))
For Each ctlID As String In myControlList
controlCounter += 1
Dim hyper As New HyperLink()
hyper.ID = ctlID
Dim lineBreak As New LiteralControl("<br />")
PlaceHolder1.Controls.Add(hyper)
PlaceHolder1.Controls.Add(lineBreak)
Next
End Sub
Protected Sub Page_Load(ByVal sender As Object, ByVal e As EventArgs)
If Not IsPostBack Then
myControlList = New List(Of String)()
ViewState("myControlList") = myControlList
End If
End Sub
Protected Sub Button1_Click(ByVal sender As Object, ByVal e As EventArgs) Handles Button1.Click
controlCounter += 1
Dim hyper As New HyperLink()
hyper.Text = "a new text Box"
hyper.ID = "hyperlink" + controlCounter.ToString()
Dim lineBreak As New LiteralControl("<br />")
PlaceHolder1.Controls.Add(hyper)
PlaceHolder1.Controls.Add(lineBreak)
--> myControlList.Add(hyper.ID)
ViewState("myControlList") = myControlList
End Sub
End Class
please help me out. Thanks.
A button click initiates a postback, and you only set myControlList to a thing if the request is not a post back, so it's nothing.
If you're wanting to create the list on page load, and then only keep adding to it with subsequent clicks, say, then you'll need to shove myControlList into the Session, or something, after creating it, then on button click retrieve it again, add to it, and re-set it in the Session.
To do this add and getting from the Session stuff, do,
Session("someDistinctKey") = myControlList;
myControlList = CType(Session("someDisctintKey"), List(Of String))
respectively.

Failure to update textbox.text

I have a relatively simple ASP.NET problem (I should think) that regrettably I am unable to solve by myself. What I am trying to do is the following:
On a page I load a number of controls (Text Boxes) programmatically;
following this load the user should be able to select a value to load into the Textbox from a panel control that is added to the page following the click of a button
Once the panel is closed, the selected text from the panel should be loaded into the textbox
However, in the vb.net statements below when run the "test" string never makes it to the textbox - any help with resolving this would be greatly appreciated.
Public Class test
Inherits System.Web.UI.Page
Protected Sub Page_Load(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load
Controls_Load()
End Sub
Public Sub Controls_Load()
Dim ttf_tb As New TextBox With {.ID = "ttf_tb"}
Master_Panel.Controls.Add(ttf_tb)
Dim ttf_button As New Button
Master_Panel.Controls.Add(ttf_button)
AddHandler ttf_button.Click, AddressOf TTF_BUTTON_CLICK
End Sub
Public Sub TTF_BUTTON_CLICK(sender As Object, e As EventArgs)
Dim str As String = sender.id
Dim panel As New Panel
panel.ID = "TTF_Panel"
panel.Width = 300
panel.Height = 300
Master_Panel.Controls.Add(panel)
panel.BackColor = Drawing.Color.Black
panel.Style.Add(HtmlTextWriterStyle.Position, "absolute")
panel.Style.Add(HtmlTextWriterStyle.Left, "200px")
panel.Style.Add(HtmlTextWriterStyle.Top, "100px")
panel.Style.Add(HtmlTextWriterStyle.ZIndex, "100")
Dim CL_Button As New Button
CL_Button.ID = "TTF_Close_" & Replace(str, "TTF_Button_", "")
panel.Controls.Add(CL_Button)
AddHandler CL_Button.Click, AddressOf TTF_Close_Button_Click
End Sub
Public Sub TTF_Close_Button_Click(sender As Object, e As EventArgs)
Dim ttf_tb As TextBox = Master_Panel.FindControl("ttf_tb")
ttf_tb.Text = "Test"
Dim panel As Panel = FindControl("TTF_Panel")
Master_Panel.Controls.Remove(panel)
End Sub
End Class
I think you need to re-create your controls in the Page_Init method. It's been a while since I've done web forms but I think it's something like:
When a user clicks the button a post back is fired. This re-creates a new instance of your class, creates the controls on the page, assigns any form values then calls your Page_Load event.
The problem is you are creating your controls too late, so the forms values are never assigned correctly.
You should create / recreate your dynamic controls in the Init event:
Protected Sub Page_Init(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Init
Controls_Load()
End Sub
This should allow you to maintain their state across PostBacks.
For more information about this topic, see the MSDN article on the ASP.NET Page Life Cycle.

VB.net/Asp.net loading a control programatically with a public property to be set

I have a vb.net asp application where I'm loading a control (from another control on a page). I want to set a variable between the two controls when it loads.
This is where I load the control:
Protected Sub Page_Load(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load
Dim AuditControl As Control = LoadControl("~/controls/auditcompanies.ascx")
phCompanies.Controls.Add(AuditControl)
End Sub
On the control that's being loaded i've exposed the item i want to change as a property
Public Property resultType() As String
Get
Return m_resultType
End Get
Set(ByVal value As String)
m_resultType = value
End Set
End Property
Basically all it is doing is setting a parameter for my table adaptor
Public Sub Load_Data()
dtblog = New dsDECorp.ClientInfoDataTable
dtblog = tablog.GetAudits(m_resultType)
For Each rClient As dsDECorp.ClientInfoRow In dtblog
CID = rClient.ClientID
ClientName = rClient.CompanyName
Next
dtblog.Dispose()
End Sub
How do I pass the parameter through the property from the first control to the second when it loads?
Thanks
Tom
I'm a C# guy so forgive me if I make any syntax errors but the following should work for you:
Protected Sub Page_Load(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load
Dim AuditControl As Control = LoadControl("~/controls/auditcompanies.ascx")
Dim AuditControlType As Type = AuditControl.GetType()
Dim AuditField As FieldInfo = AuditControlType.GetField("resultType")
AuditField.SetValue(AuditControlType, "Your Value")
phCompanies.Controls.Add(AuditControl)
End Sub

Asp.Net Null Reference Exception on Event Handler for Dynamic Controls

I've created some dynamic controls on page load and added an event handler to handle the click event of a dynamic link button. Within the sub of the click event handler, I need to reference some other (non-dynamic) controls on the page and change their value. However, I get a null reference exception - object not set to an instance of an object - each time I try to reference a control on the page (in this case label1). What am I doing wrong in creating these dynamic controls or with my event handler? Thanks!
Protected Sub Page_Load(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load
'Get the data to populate the controls
Dim oMySqlData As New MySqlDataProvider
PlaceHolder1.Controls.Add(CreateExistingNotesHTML(oMySqlData.GetParentNotes("104628"), oMySqlData.GetChildNotes("104628")))
End Sub
Public Sub OnCommentClick(ByVal sender As Object, ByVal e As EventArgs)
'The event handler for the link buttons
Label1.Text = "You clicked " & DirectCast(sender, LinkButton).ID
End Sub
Public Function CreateExistingNotesHTML(ByVal dtParent As DataTable, ByVal dtChild As DataTable) As HtmlGenericControl
'The routine that creates the dynamic controls
Dim divContainer As New HtmlGenericControl("div")
For Each drParent As DataRow In dtParent.Rows()
divContainer.Controls.Add(WriteNote(drParent.Item("NoteId").ToString(), drParent.Item("UserName").ToString(), drParent.Item("ItemNote").ToString, CDate(drParent.Item("InsertDate")), "note"))
Next
Return divContainer
End Function
Private Function WriteNote(ByVal NoteId As String, ByVal UserName As String, ByVal ItemNote As String, ByVal InsertDate As DateTime, ByVal DivClass As String) As HtmlGenericControl
Dim div As New HtmlGenericControl("div")
div.ID = "d" & NoteId
div.Attributes.Add("class", DivClass)
div.Controls.Add(New LiteralControl(" ยท "))
'Add the dynamic link buttons
Dim lnkComment As New LinkButton
lnkComment.ID = "l" & NoteId
lnkComment.Text = "Comment"
lnkComment.Style("Text-decoration") = "none"
AddHandler lnkComment.Click, AddressOf oNotes.OnCommentClick
div.Controls.Add(lnkComment)
Return div
End Function
With this line
Dim oNotes As New EbayItemNotes
AddHandler lnkComment.Click, AddressOf oNotes.OnCommentClick
You are handling this event outside of your page and within the EbayItemNotes class, how does this class know anything of Label1 that resides in your page?
Could it be that you need to pass your label in as well..
Dim oNotes As EbayItemNotes = new EbayItemNotes(label1)
inside EbayItemNotes constructor
public sub New(lbl as Label) //store this label for use in event handler..

Resources