asp.net VB programmatically add multiple buttons with unique events - asp.net

I have a quoting system that can generate several variants of a quote. these quotes are displayed on a screen for sales staff to compare and choose which is the most suitable. Is it possible to programmatically create a button and click event for each quote that is generated?
Each quote needs a save button and a remove button. both would fire functions and pass in the quite ID.
Can anyone point me in the correct direction for this? the amount of quotes and buttons that could be on the page is limitless.
Many thanks for your help.

Set CommandName and CommandArgumentof your button template and catch the event inside ItemCommand event of your repeater
<asp:Repeater runat="server" ID="rptrQuites">
<ItemTemplate>
<asp:LinkButton ID="btnSave" Text="Save" CommandName="Save" CommandArgument="<%#Eval("QuiteID")"%>></asp:LinkButton>
</ItemTemplate>
</asp:repeater>
and in code behind
Protected Sub rptrQuites_ItemCommand(source As Object, e As RepeaterCommandEventArgs) Handles rptrQuites.ItemCommand
If e.CommandName = "Save"
' Put your code here
End If
End Sub

Related

Asp.net textbox returns empty string when enter key is pressed at the end of text vb.net

I am very new to the world of aspx, web forms. But I am assigned to development of webform due to some circumstances. I am somehow struggling and surviving in this. I have a problem, may be if someone who is familiar with this, can help me understand is very much appreciable.
Problem:
I am created a search box functionality successfully in an aspx webform with codebehind as vb. But the problem is, when I type some text in this search box and press enter, it reloads to initial state rather than show up the search results. It works well when we just type text in it and do not press enter. For every letter I type in the box, in displays with matching search results. I just am wondering why is this not working if I type text and press enter at the end of text for example like google search. For ex: I typed "test" in searchbox and press enter. Results appear perfect until I press enter key. Once I press enter, it goes back to original state how ever it was.
Investigation:
I debugged it and found that when enter is pressed, the value in textbox becomes empty. I am unable to understand why is it getting empty even if text is present in text box. I tried onkeypress="return event.keyCode!=13" in
<asp:TextBox ID="SearchTextBox" runat="server" onkeypress="return event.keyCode!=13" CssClass="txt"></asp:TextBox> so as not to return empty value when enter is pressed. But it did not work.
Dim searchkey As String
searchkey = SearchTextBox.Text.
searchkey returns emtpy string and not "test" string. But why? How can I overcome it?
Looking for: Is there a possibility that I can get the text value present in textbox when enter is pressed.
I appreciate your help and new learning for me
Do not use onkeypress directly like this onkeypress="return event.keyCode!=13"
create a common js file and use it anywhere you want, you can modify also in one js.
use common js file and create a function and use on your code via link like this <script src="~/js/common.js"></script>
Here is the js code to prevent Enter key:
function DisbleEntr(evt) {
if (evt.key == "Enter") {
return false;
}}
and use in your code like this:
<asp:TextBox ID="SearchTextBox" runat="server" onkeypress="return DisbleEntr(event);" CssClass="txt"></asp:TextBox>
hope this will help you
Well, first up, enter key tends to mean submit the page.
And ALSO note that a simple hit of the enter key will trigger the FIRST button found on that page!!!!
Say we have this simple grid and at the bottom I have a search box, and a search button. Real simple, say like this:
<asp:GridView ID="GridView1" runat="server" AutoGenerateColumns="False"
DataKeyNames="ID" CssClass="table table-striped" Width="50%">
<Columns>
<asp:BoundField DataField="FirstName" HeaderText="FirstName" />
<asp:BoundField DataField="LastName" HeaderText="LastName" />
<asp:BoundField DataField="HotelName" HeaderText="HotelName" />
<asp:BoundField DataField="Description" HeaderText="Description" />
<asp:TemplateField HeaderText="Edit Hotel" ItemStyle-HorizontalAlign="Center">
<ItemTemplate>
<asp:Button ID="cmdEdit" runat="server"
Text="Edit" CssClass="btn" OnClick="cmdEdit_Click" />
</ItemTemplate>
</asp:TemplateField>
</Columns>
</asp:GridView>
<br />
<asp:Label ID="Label1" runat="server" Text="Search For Hotel" Font-Size="Large"></asp:Label>
<asp:TextBox ID="txtSearch" runat="server" Style="margin-left:10px"></asp:TextBox>
<asp:Button ID="cmdSearch" runat="server"
Text="Search" Style="margin-left:10px"
CssClass="btn" />
Now, code to load above say this:
Protected Sub Page_Load(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load
If Not IsPostBack Then
LoadGrid()
MyEditHotelC.ShowGrid(True)
End If
End Sub
Sub LoadGrid()
Dim rstData As DataTable
rstData = MyRst("SELECT * FROM tblHotelsA ORDER BY HotelName")
GridView1.DataSource = rstData
GridView1.DataBind()
End Sub
Note SUPER DUPER VERY VERY close - note in above, that on page load, I ALWAYS check for IsPostback.
Remember, for any button click or any post-back the page load event fires. Including any button click - so code that setups up a grid, setups text box, or ANYTHING? - you only want to run such code one time.
We see/have about 5 posts a week here in which someone drops in a combo box, selects a value, and clicks a button - and then the selected value goes away!!!
Why? Because they had code in the page load event to load up the combo box, and thus each and every time that setup code to load the combo box runs each time and blows out your combo box selection.
BIG HUGE LESSON:
Quite much EVERY web page you build that has ANY setup code will thus have the above If NotPostBack code stub. I recon the last 100+ pages I built work this way.
So, ALWAYS make sure you include that If Not Postback stub for page setup code, and NEVER forget to do this.
Ok, so we run the page and we have this:
Now the first rule:
When you hit a enter key inside of a text box, the FIRST button on the page we find will trigger.
So, looking at above, what will happen?
Turns out the FIRST button on the page in tucked away in the GridView!!!!
So, if I type in to search box, and hit enter key, then this button will be clicked on:
Surprise!!!!
Now, why is this most of the time never a issue?
Well, in most cases, you don't have a lot of buttons and I can/could fix above, by simple moving the search box, and button to the top, say like this:
So, it turns out by luck, we find in most cases this is not a issue.
And a slick easy way to fix this issue?
Well, drop in a button at the VERY top of the page - set style = "display:none" (to hide the button, and this issue is fixed - all without any special code).
eg this:
<form id="form1" runat="server">
<asp:Button ID="catchEnter" runat="server" Text="Button"
OnClientClick="return false" style="display:none"/>
So, VERY first control on page.
next up:
So, VERY much keep the above in mind.
Next issue:
For every letter I type in the box, in displays with matching search results.
Ok, so you have some type of auto-complete code. That is a HUGE issue - and there are about 20+ libraries and examples floating around on the internet. You don't mention what code library you adopted (maybe the one from jQuery.UI, maybe the one from the ajaxtoolkit - but boatloads of systems exist).
Or MAYBE you rolled your own? I actually VERY high recommend the ajaxtoolkit, since it has a really nice autocomplete extender - and it uses ajax calls without postbacks for this setup.
Your issue is thus above and in summary:
The text box has some library code attached - gets setup in page load - but you failed to adopt and is the IsPostBack = false test.
The enter key not being trapped - and thus above - first button ANYWHERE in the page - even those tucked away in a grid view or anywhere else is thus causing a page post-back.
You not shared if your auto complete setup DOES a post-back, but again if it does, then that's often the issue.
So to prevent enter key clicking on first button, you can add the above "trick" and drop in a hidden button, and one that when clicked on does not cause a post-back due to enter key.
Since I have the ajax tool kit installed?
I can do this:
I choose Add extender for that text box, and choose this:
So, it puts in this markup for me:
<ajaxToolkit:AutoCompleteExtender ID="TextBox1_AutoCompleteExtender" runat="server"
BehaviorID="txtSearch_AutoComplete"
DelimiterCharacters=""
ServiceMethod="SearchCustomers"
MinimumPrefixLength="1"
CompletionInterval="100"
EnableCaching="false"
CompletionSetCount="40"
TargetControlID="txtSearch">
</ajaxToolkit:AutoCompleteExtender>
Nice about above? I can set how many chars before search. I can set the timign to update etc. And I not had to write one line of js code either!!!
So the above looks like this now
So, the only part I had to setup and write was the code behind for this search.
That was this:
<WebMethod()>
Public Shared Function SearchCustomers(ByVal prefixText As String, ByVal count As Integer) As List(Of String)
Using conn As SqlConnection = New SqlConnection()
conn.ConnectionString = My.Settings.TEST4
Using cmd As SqlCommand = New SqlCommand()
cmd.CommandText = "select HotelName from tblHotels where HotelName like #SearchText + '%'
ORDER BY HotelName"
cmd.Parameters.AddWithValue("#SearchText", prefixText)
cmd.Connection = conn
conn.Open()
Dim customers As List(Of String) = New List(Of String)()
Using sdr As SqlDataReader = cmd.ExecuteReader()
While sdr.Read()
customers.Add(sdr("HotelName").ToString())
End While
End Using
conn.Close()
Return customers
End Using
End Using
End Function
But, all the rest? No extra code.
So, I would consider to adopt a stadnard library (jquery.UI maybe, or the above ajaxtoolkit).

How do I prevent __DoPostBack refreshing an ASPX page?

I have a JS function in an ASPX page that performs a __doPostBack to a vb.net code behind. The problem is that it is forcing the page to refresh. How can I prevent this? My code below...
JS:
__doPostBack('', 'test');
VB.NET:
Protected Sub Page_Load(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load
If IsPostBack Then
Select Case Request.Form("__EVENTARGUMENT")
Case "test"
RadMediaPlayer1.Source = url
End Select
End Sub
Thanks!
There is one easy way, and then one hard way.
The first issue? asp.net web pages are in fact designed to near ALWAYS have and endure post-backs.
This quite much means that any button, any combo box, or just about anything on that page to run some code behind WILL cause a page post-back.
And thankfully due to automatic "view state" management, most controls, and even a grid view, or even a combo box selection will correctly maintain its values for you (its view state).
So, if you don't want the whole page to post back and refresh?
Then you can drop in a plane jane asp.net button, and say whatever it is you want to "only update", then try using what is called a update panel.
Try a quick test page like this:
<form id="form1" runat="server">
<div>
<asp:TextBox ID="TextBox1" runat="server"></asp:TextBox>
<br />
<asp:Button ID="Button1" runat="server" Text="Button" />
</div>
</form>
And our code behind like this:
Protected Sub Page_Load(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load
End Sub
Protected Sub Button1_Click(sender As Object, e As EventArgs) Handles Button1.Click
TextBox1.Text = Date.Now
System.Threading.Thread.Sleep(700)
End Sub
Now, I put in a 3/4 of second delay - just to help you see the effects of this (you don't want that delay sleep() in your actual code.
Ok, now run the above page, click on the button. You see the traditional post-back, you see the browser "spinner"/wait occur, and then the text box is updated.
Now, lets use what is called a update panel - and I am going to suggest you try one.
You can even dump/drop the JavaScript you have now.
So, you have to drop into the page a script manager, and then move your content inside of he update panel. It will now look like this:
<form id="form1" runat="server">
<asp:ScriptManager ID="ScriptManager1" runat="server"></asp:ScriptManager>
<div>
<asp:UpdatePanel ID="UpdatePanel1" runat="server">
<ContentTemplate>
<asp:TextBox ID="TextBox1" runat="server"></asp:TextBox>
<br />
<asp:Button ID="Button1" runat="server" Text="Button" />
</ContentTemplate>
</asp:UpdatePanel>
</div>
</form>
Give above a try - note how the page don't post-back any more? How cool is that!!!
So, add update panel, content template. And move your button, and the adMediaPlayer1 into that panel.
You don't even need to adopt any JavaScript here. Drop in a plane jane button, and just have normal code behind for that button. Say like this:
Protected Sub Button1_Click(sender As Object, e As EventArgs) Handles Button1.Click
RadMediaPlayer1.Source = "some real url goes here"
End Sub
A few things:
While this looks, feels and appears to NOT do a post back and the .net system will wire this up for you automatic - VERY much like a ajax call?
Don't put too much inside of those update panels.
and keep in mind, while this does not seem to do a post back? In fact this results in what we call a "partial" post back. The page load event even will fire.
Note that code behind CAN ONLY now modify controls inside of that update panel. Other controls on the page are off limits. (unless you move them into that update panel also).
But, dump your JavaScript button or code for the post back. Just move in the media control and your button to inside of that up date panel. Give this a try - you not see a post back - you not see the browser "spinner"/wait run at all.
This feature is great - but a not a cure all.
The next way to do this?
Is you can setup what is called a ajax call. This can call code behind, but keep in mind the code behind can't update controls on the page (due to no post-back). If you don't do a post-back, then code behind can't touch controls on the page.
This would suggest that you have a client side button - click on it, it runs JavaScript, calls some code behind, code behind returns a result, and then in JavaScript you stuff/change the URL of the given control. Since you changing that URL in pure JavaScript at this point? You probably don't even need to write or call code behind anyway.
but, try the update panel - they are very useful. But, keep in mind behind, the .net system is doing a bit of fakery to achieve this goal, and what a partial page post- back does occur.
Edit: pass value from js and click button
So, as noted, if you have a post back, you get page refresh!!! - that's what the command does and means!! So, you can't say I dont want to post back and not refresh the page, and then do a post back!!!
However, as noted, your js code is "obviously" a much larger example, and you sharing of JUST the __DoPostBack() in js is as you noted a larger set of code and routines here.
However, I still suggest you use a update panel.
You can keep 99% of your js code now, and just remove the _dopost back.
Move your case statement code to a button. (yes, a button click code stub).
What we THEN do is this:
The js code can figure out and do whatever it needs. Obviously we reach a point in which a VALUE of some type has to be passed to the server. And then what we will do is then use js code to CLICK the button - the ONE inside of the update panel. This will and should prevent a page refresh. And we pass the value by using a asp.net hidden field control (you could even use a hidden text box - but it don't matter - hidden field is probably better).
So, the pattern, and code will look like this:
We drop a button, hidden field, and that other video or whatever control is is the page - all inside the update panel.
then your js code? It runs, gets the final value. We shove that value into a hidden field control, and then use js to click the button - also inside of that panel.
Thus, you move your on load code + case statement to the button click code.
Like this:
Protected Sub Page_Load(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load
End Sub
Protected Sub Button1_Click(sender As Object, e As EventArgs) Handles Button1.Click
' get value passed from js
Dim strMyValue As String = Me.HiddenField1.Value
Debug.Print(strMyValue)
Select Case strMyValue
Case "test"
Case "zoo"
Case "my fun test"
End Select
End Sub
And the markup is this:
<asp:ScriptManager ID="ScriptManager1" runat="server"></asp:ScriptManager>
<div>
<asp:UpdatePanel ID="UpdatePanel1" runat="server">
<ContentTemplate>
<asp:TextBox ID="TextBox1" runat="server"></asp:TextBox>
<br />
<asp:Button ID="Button1" runat="server" Text="Button" ClientIDMode="Static" />
<br />
<asp:HiddenField ID="HiddenField1" runat="server" ClientIDMode="Static" />
</ContentTemplate>
</asp:UpdatePanel>
<asp:Button ID="Button2" runat="server" Text="js post back"
OnClientClick="mypost();return false;"
/>
<script>
function mypost() {
// set value to pass to button click
$('#HiddenField1').val("my fun test")
$('#Button1').click()
}
</script>
</div>
So, in place of your doPostback, you set the hidden field, and then with js click the button. (once you get this workng, then hide the button with style="display:none"
Of course, you proably have a bunch of postback in your code.
So, make a js function called MyPostBack, say like this:
function MyPostBack(sValue) {
// set value to pass to button click
$('#HiddenField1').val(sValue)
$('#Button1').click()
}
Now, you can replace all your _DoPostBack('', 'test')
With MyPostBack('test')
So, in the update panel, put the hidden field, the button, and that other control. And your js code will now "click" that button in the panel.
Note that the js code above does assume you using jQuery. However, you can code in pure js, and not necessary use jQuery short hand as I did above.

Webform buttons displaying blank page

The bug I'm trying to solve is that the buttons on my .aspx page that correspond to methods in the .vb file all return a blank page without actually getting to the vb code (no breakpoints I've put on these methods get triggered). There is no redirect as the URL doesn't change it simply registers the button click and then its handler gives a blank page. I thought at first that this would have something to do with doPostBack but even after putting "CausesValidation="false" " this still continues. I've recreated the button in the designer window just to be extra sure that the button points to code and the program knows it but still no luck.
Here is what the button itself looks like:
<asp:Button ID="btnFreshTest" runat="server" CausesValidation="true" Text="Save User" ClientIDMode="Static" width="100px" ToolTip="Save changes" Height="35px" />
Here is what the visual basic method code looks like, yes its simple but this is for a test:
Protected Sub btnFreshTest_Click(sender As Object, e As EventArgs) Handles btnFreshTest.Click
Dim testString2 As String = "abc"
End Sub
Even if you don't have a solution given the lack of information, if you have any pointers that I could use like places to look for an error or somewhere to put a breakpoint with chrome tools, I would greatly appreciate it.
Ok, so we drop this into a page:
<asp:Button ID="btnFreshTest" runat="server" CausesValidation="true"
Text="Save User" ClientIDMode="Static"
width="100px" ToolTip="Save changes" Height="35px" />
So we see this:
Now do NOT JUST TYPE in the event stub - double click on the button above, and you now have this:
Protected Sub btnFreshTest_Click(sender As Object, e As EventArgs) Handles btnFreshTest.Click
Dim testString2 As String = "abc"
Console.WriteLine("Value of test string = " & testString2)
End Sub
And when we run, then we get this:
So, you may well have messed up the event, but if you JUST drop in that button (say a cut + paste from example code), then the event stub will not automatic wire up - you have to click on it.
And note VERY close that the button does not see, nor have a event defined IN the markup - but you will see it in the property sheet for that button like this:
And you can in markup actually force/type in the event define, and intel-sense will do this:
In fact you MUST DO this if the button is inside of a repeater/gridview/list view etc., since you can't double click on the button in the desinger anyway. So additional information here in regards to if some data repeating type of control is surrounding the button. A button is often part of MUCH markup, and depending on how it is nested, a simple click on the button is not always possible.
So, try typing in the OnClick= (and when you hit "=", you should get intel-sense, and try wire up the button that way.

ASP.NET GridView empty on postback

Having an issue with an ASP.NET GridView is empty on postback that I need some help with. I think it may have something to do with the ViewState not being setup. Anyhow I originally had the code working on single user-form until I refactored code.
Now to paint the picture I have now both a master page and a base form. My master page has the place holder and on my actual user-form I have placed the GridView within the place holder bounds as follows:
<asp:Content ID="Content2" ContentPlaceHolderID="ContentPlaceHolderMainBody" Runat="Server">
<asp:GridView ID="data" runat="server" AutoGenerateColumns="false" EnableViewState="true" ...>
...
</asp:GridView>
</asp:Content>
One of fields in the GridView is an editable comments field mutli-line textbox (the rest are non editable):
<asp:TemplateField HeaderText="Comments">
<ItemTemplate>
<asp:TextBox ID="TextBoxComments" runat="server" TextMode="MultiLine" Rows="4" Columns="40" Text='<%# Bind("Comment")%>' />
</ItemTemplate>
<EditItemTemplate>
<asp:TextBox ID="TextBoxCommentsEdit" runat="server" TextMode="MultiLine" Rows="4" Columns="40" Text='<%# Bind("Comment")%>' />
</EditItemTemplate>
</asp:TemplateField>
I edit one of the rows and click a submit button to postback. The GridView has 10 rows to enter into however on postback there are zero rows so my saving is lost!
My base form contains the code in the OnInit event to load the submit button and thus also handles the click event.
My OnLoad event I call the base Onload which inturn calls my user form's Page_Load handler code which has one line of code namely:
Protected Sub Page_Load(ByVal sender As Object, ByVal e As EventArgs) Handles Me.Load
MyBase.data = Me.data
End Sub
and in the BaseForm is declared as:
Protected WithEvents data As GridView
Protected Overrides Sub OnLoad(e As EventArgs)
MyBase.OnLoad(e)
If Not Page.IsPostBack Then
...
BindData(...)
...
End If
End Sub
in this way I can also handle all GridView events in the BaseForm.
So somewhere between the master/baseform/userform/viewstate relationship my GridView data is lost on PostBack. Any ideas?
On your Page_Load, bind the data only if IsPostBack is false.
You click on submit button that submit button fire RowUpdating event and that event contain query for update database table and after executed update query call BindData() function in your code .
Three in row I think for myself answering my own question - hooray! I do not know if that makes me intelligent or dumb because I have to search for more that a day to find a solution. Perhaps I did not give out enough information or it was not clear and this is what happens when you do things for the first time and you do not have a clue what you are doing. The vital information which was maybe not implied but hinted at, which I will spell it out for anyone else that might have the same problem, is I left out mentioning in my OnInit method I call the following code:
Dim cpl As ContentPlaceHolder = Master.FindControl("ContentPlaceHolderFooter")
btnUpdate = New Button
btn.ID = "btnUpdate"
cpl.Controls.Add(btnUpdate)
I know the purest will say why did you not add the button to the footer of the grid as opposed to an additional content placeholder in the master page - well with egg on my face I didn't.
Anyhow I moved the code above to the CreateChildControls overridable method and I also required an additional call to EnsureChildControls in my OnLoad event so my OnInit method with emphasis disintegrated!##%^* Why? Well the answer was hinted at within the answer to the other question asked on this site I mentioned in my second comment to "Rajan Chauhan" that I checked out and that is apparently whenever you iterate through the collection of controls you mess with the ViewState (hey I am just re-iterating what was said in the other post I have no authority on the matter) before it gets loaded so calling Master.FindControl is a no-no inside OnInit!
However, saying all that my RowUpdated event does not fire as I am actually editing in view mode because of my ItemTemplate markup so I will stick with what I have as my btnUpdate_Click event still works as before i.e. it does some magical code that I found on some other site that checks each row one by one for change of data and then updates that particular row only. Well I can as there is only 10 rows at most so I do not overload the ViewState too much and if it is important to know I also use paging so in reality I have more than 10 rows but did not want to mention that as I thought that might add to the confusion.

leave event for textbox in asp.net vb.net

I'm looking for a solution for the textbox leave event in asp.net vb.net.
I have searched but Didn't get the right solution, what I'm actually doing is.
I have textbox in which a user write the Product Id number however the focus moved from the textbox then all the related data should be displayed on the concern textboxes.
Their is no textbox_lostfocus event or textbox_keydown event available in ASP.Net. You can do the same by writing the code in TextChanged event of the Text Box.
Your code will be like the following :
Private Sub txtamount_TextChanged(ByVal sender As Object, ByVal e As System.EventArgs) Handles txtamount.TextChanged
//Your code comes here
MsgBox(txtamount.Text)// sample display
End Sub
This code will give result only when you add AutoPostBack ="true" with your Textbox design.
ie., the ASP code for the textbox will be :
<asp:TextBox ID="txtamount" runat="server" AutoPostBack ="true" />
Hope that this is actually your are asking for.

Resources