ModalPopup Not Showing (ASP.NET/VB) - asp.net

I can't figure this out. I've tried everything and am pulling my hair out. I can't seem to call this:
<asp:Button ID="Button3" runat="server" Text="Button" style="display: none;" />
<asp:ModalPopupExtender ID="ModalPopupExtender2" runat="server"
targetcontrolid="Button3" popupcontrolid="Panel1"
popupdraghandlecontrolid="Popup2" drag="true"
backgroundcssclass="ModalPopupBG">
</asp:ModalPopupExtender>
<asp:Panel ID="Panel1" runat="server">
<div class="HellowWorldPopup">
<div class="PopupHeader2" id="Popup2">
</div>
<div class="Controls">
<center><table border=0 cellpadding=0 cellspacing=0><tr><td><img src="Images/ajax-loader.gif" /></td><td> Please Wait...</td></tr></table></center>
</div>
</div>
</asp:Panel>
By using this:
Protected Sub LoginButton_Click1(ByVal sender As Object, ByVal e As EventArgs)
Me.ModalPopupExtender2.Show()
System.Threading.Thread.Sleep(1000)
Me.ModalPopupExtender2.Hide()
End Sub
What, on Earth, is wrong with my code? The button executes, and when I step through I get a 'There is no source code available for the current location' when it hits Me.ModalPopupExtender2.Show().
Any ideas?
Thanks,
Jason

You need to allow the Response to the LoginButton_Click1 to complete before you put the thread to sleep and hide the popup. In other words, take out
System.Threading.Thread.Sleep(1000)
Me.ModalPopupExtender2.Hide()
You'll need to use some other mechanism to hide the popup after your timeout. One common way is to set a javascript timeout on the client and have it close the window.
The javascript timeout function would have code like this in it (make sure it's after the scriptmanager on the page).
var mpu = $find('ModalPopupExtender2');
mpu.hide();

Related

ASP.NET assign button onclick at runtime

I am using ajax modal popup dialog to make users confirm their action. Since I have several scenarios where the user needs to confirm the action, I would like to re-use the same popup dialog, only changing which event is fired when the user click btnYes (confirming the action).
In code behind (VB) I assign the message for the popup:
lblMessageConfirm.Text = strMessage
Then, before opening the dialog, I would like to assign the event that btnYes will fire if the user clicks. I tried the methods below and none seems to work:
AddHandler btnYes.Click, AddressOf Test '(this event does not do anything)
And also
btnYes.Attributes.Add("onclick", "Test") '(this returns an error “Test is undefined”)
Test1 is the sub I want to assign to “Onclick” and it is in the code behind in the page where the popup is set up:
Protected Sub Test(sender As Object, e As EventArgs)
MsgBox("Test ")
End Sub
I open the dialog:
ModalPopupExtender2.Show()
Here is the html for the popup – it does show up, so the only problem is trying to assign onclick event. When I add the “onclick” in the HTML, the Test sub runs
<cc1:ConfirmButtonExtender ID="cbe" runat="server"
DisplayModalPopupID="ModalPopupExtender2" TargetControlID="lnkDummy">
</cc1:ConfirmButtonExtender>
<cc1:ModalPopupExtender ID="ModalPopupExtender2" runat="server"
PopupControlID="pnlPopup2"
TargetControlID="lnkDummy"
CancelControlID="btnNo" >
</cc1:ModalPopupExtender>
<asp:Panel ID="pnlPopup2" runat="server" CssClass="modalPopup"
Style="display: none">
<div class="ModalHeader" runat="server">
Please Confirm ...
</div>
<div class="ModalBody" runat="server">
<asp:Label ID="lblMessageConfirm" runat="server">
</asp:Label>
</div>
<div class="ModalFooter">
<asp:Button ID="btnYes " runat="server"
CSSClass="ModalButton" Text="OK" />
</div>
</asp:Panel>
With the following code Test runs:
<asp:Button ID="btnYes " runat="server" CSSClass="ModalButton" Text="OK"
onclick="Test"/>
I have this working with 2 Yes buttons and making the correct one visible based on the scenario, but adding more scenarios where the user needs to confirm will mean adding more buttons...

Server cannot set content type after HTTP headers have been sent - after error within an updatepanel

I'm getting the following error: Server cannot set content type after HTTP headers have been sent. I have looked around online, including some of the SO questions with exactly this error, but none have resolved my issue. Here is my particular scenario:
I have an asp.net gridview that is inside of an update panel (which also happens to be inside of a modalpopupextender). The gridview has a template field with an imagebutton that, when clicked, downloads a PDF. All works well until I run into an error trying to download. I handle the error inside the Gridview.RowCommand event, and the page doesn't change back on the client like I want. However, if I click the download again, the file doesn't download, and I catch the error inside ScriptManager.AsyncPostBackError event "Server cannot set content type after HTTP headers have been sent." Thanks in advance!
Here is my code:
--Default.aspx--
<asp:HiddenField ID="hdnHiddenField" runat="server" />
<cc1:ModalPopupExtender ID="hdnHiddenField_mpeModalPopup" runat="server" Enabled="True" TargetControlID="hdnHiddenField"
CancelControlID="lnkClose" PopupControlID="pnlPanel" BackgroundCssClass="modalBackground"></cc1:ModalPopupExtender>
<asp:Panel ID="pnlPanel" runat="server" BorderStyle="Double" Width="50%" Height="75%" CssClass="modalPopup" style="overflow: auto; display: none">
<div class="modalHeaderClose">
<asp:LinkButton ID="lnkClose" runat="server" Text="Close [X]"></asp:LinkButton>
</div>
<cc1:Accordion ID="accdnPolicyInfo" runat="server" SelectedIndex="0" RequireOpenedPane="false">
<Panes>
<cc1:AccordionPane ID="accpnlDocuments" runat="server">
<Header>
<div class="accordionHeader">Documents</div>
</Header>
<Content>
<asp:UpdatePanel ID="upDocuments" runat="server" UpdateMode="Conditional">
<ContentTemplate>
<div style="text-align: center; padding: 0 10px 10px 10px;">
<asp:GridView ID="gvGridView" runat="server" AutoGenerateColumns="False" Width="100%" ShowHeaderWhenEmpty="True">
<Columns>
<asp:TemplateField>
<ItemTemplate>
<asp:ImageButton ID="imgDownloadPDF" runat="server"
CommandArgument='<%# Bind("ImageKey") %>' CommandName="DownloadDocument"
ImageUrl="~/images/PDF-download.png" ToolTip="Download file to your computer" />
</ItemTemplate>
</asp:TemplateField>
</Columns>
<EmptyDataRowStyle ForeColor="Red" HorizontalAlign="Center" />
</asp:GridView>
</div>
</ContentTemplate>
</asp:UpdatePanel>
</Content>
</cc1:AccordionPane>
</Panes>
</cc1:Accordion>
</asp:Panel>
--Default.aspx.vb--
Private Sub gvPolicyDocs_RowDataBound(ByVal sender As Object, ByVal e As System.Web.UI.WebControls.GridViewRowEventArgs) Handles gvPolicyDocs.RowDataBound
Dim imgDownloadPDF As ImageButton = e.Row.FindControl("imgDownloadPDF")
If imgDownloadPDF IsNot Nothing Then
ScriptManager.GetCurrent(Page).RegisterPostBackControl(imgDownloadPDF)
'I just tried changing to RegisterAsyncPostBackControl method and found that I receive the same error even on the first attempt
End If
End Sub
Protected Sub gvPolicyDocs_RowCommand(ByVal sender As Object, ByVal e As System.Web.UI.WebControls.GridViewCommandEventArgs) Handles gvPolicyDocs.RowCommand
Try
StreamPDF(e.CommandArgument, False)
Catch ex As Exception
ErrorHandler.HandleError(ex) 'sends out an email and returns back; ErrorHandler is an object I created
End Try
hdnHiddenField_mpeModalPopup.Show() 'otherwise modal popup disappears after return from postback
End Sub
Private Sub StreamPDF(ByVal strImageKey As String)
Dim dtImagePaths As DataTable
Dim oPDFManager As New PdfManager 'from ASPPDF library
Dim bytes() As Byte
Dim strImagePath As String = String.Empty
If String.IsNullOrEmpty(strImageKey) Then
Throw New Exception("Invalid Image Key")
End If
'Get image path from database
...
...
strImagePath = dtImagePaths.Rows(0).Item("ImagePath")
bytes = oPDFManager.OpenDocument(strImagePath).SaveToMemory()
'I checked that on the run after the error, bytes contains exactly what I want - so when I write it to a file locally, I can see the PDF
With Current
.Response.BufferOutput = False 'tried true and false
.Response.Clear()
.Response.ClearContent()
.Response.ClearHeaders()
.Response.ContentType = "application/pdf"
.Response.AddHeader("Content-Disposition", String.Format("{0}; filename={1}.pdf", IIf(bDownloadFile, "attachment", "inline"), strImageKey))
.Response.AddHeader("Content-Length", bytes.Length)
.Response.BinaryWrite(bytes)
.Response.Flush()
.Response.Close()
'Response.End() '--> See http://support.microsoft.com/kb/312629
.ApplicationInstance.CompleteRequest()
End With
End Sub
The UpdatePanel is probably the problem here.
Please see here.
Why won't Response.Write() export a CSV file to the browser?
Well, in case anyone else runs into this issue, this article helped me out completely. It basically indicates that you can't download and use the asyncpostback functionality (via UpdatePanel) on the same page. It demonstrates a workaround in which all of the download code is done on an entirely separate page, and that page is opened in a hidden iframe on the current page. On a side note, if you are also or instead trying to open the pdf in a new window, the same workaround applies but instead of adding an iframe to the current page, you can call window.open() in JavaScript.
So, I'm not sure how to fix this in VB, but I know the cause of this issue in C# as I have just had to deal with this issue myself.
The problem lies with the button itself. You need to register the button with the ScriptManager. You cannot do this at the PageLoad() event, you actually have to add an OnInit event to the button and add the registration there.
Example in C#:
ASP page code:
<asp:ImageButton ID="imgDownloadPDF" runat="server" onInit="imgDownloadPDF_Init" ... />
Code Behind:
protected void imgDownloadPDF_Init(object sender, EventArgs e)
{
ScriptManager.GetCurrent(this).RegisterPostBackControl(imgDownloadPDF);
}
I hope this helps.

Placeholder Code still visible when "view source code", even though placeholder visible property set to false from code behind

<asp:PlaceHolder ID="pnlThanks" runat="server" Visible="false">
<p><asp:Literal ID="lblReceipt" runat="server"></asp:Literal></p>
</asp:PlaceHolder>
<asp:PlaceHolder ID="pnlForm" runat="server" Visible="true">
<form id="form1" runat="server" class="busgroup-form">
//// All form controls
</form>
</asp:PlaceHolder>
Code Behind file:
Protected Sub submit_Click(ByVal sender As Object, ByVal e As EventArgs) Handles cmdsubmit.Click
form1.Controls.Clear()
pnlForm.Visible = False
pnlThanks.Visible = True
End Sub
So, after submitting form when "pnlThanks" placeholder is visible, I can see proper contents displayed on page. But when I do "view source" on the browser, I see the source code for form and not the content inside "pnlThanks" placeholder.
What am I doing wrong ?
You need to have all of your controls within the <form> tag, because ASP.NET depends upon the form to do postbacks, etc.
You can only have one <form> tag in your page.
Change your code to this:
<form id="form1" runat="server" class="busgroup-form">
<asp:PlaceHolder ID="pnlThanks" runat="server" Visible="false">
<p><asp:Literal ID="lblReceipt" runat="server"></asp:Literal></p>
</asp:PlaceHolder>
<asp:PlaceHolder ID="pnlForm" runat="server" Visible="true">
</asp:PlaceHolder>
</form>
Your code works as expected when I tested it. My guess is there is another pnlForm.Visible = True in your code elsewhere that is executed on your postback.
pnlThanks isn't rendered if visible=false, therefore it won't show in the source. You can use CSS (display=none) to hide it on start and change when needed.

Using multiple UpdatePanels on a single page without interfering with each other

It seems that when multiple UpdatePanels are on a single page, anytime an asyncPostBack occurs on one, all others will have their html reloaded. Is there a way around this?
Example
Example.aspx
<asp:UpdatePanel ID="UpdatePanel1" runat="server">
<ContentTemplate>
<div style="border: 1px solid black;">
<asp:TextBox runat="server" ID="txtTEST1" />
<asp:Label runat="server" ID="lblTEST1" />
<asp:Button runat="server" ID="btnTEST1" Text="AsyncPostBack1" />
<div onclick="this.innerHTML='Wooo!'">Click Me - UpdatePanel1</div>
</div>
</ContentTemplate>
</asp:UpdatePanel>
<div onclick="this.innerHTML='Wooo!'" style="padding: 1em;">Click Me. I'm not part of an Update Panel</div>
<asp:UpdatePanel ID="UpdatePanel2" runat="server">
<ContentTemplate>
<div style="border: 1px solid black;">
<asp:TextBox runat="server" ID="TextBox1" />
<asp:Label runat="server" ID="Label1" />
<asp:Button runat="server" ID="Button1" Text="AsyncPostBack2" />
<div onclick="this.innerHTML='Wooo!'">Click Me - UpdatePanel2</div>
</div>
</ContentTemplate>
</asp:UpdatePanel>
Example.aspx.vb
Protected Sub btnTEST1_Click(sender As Object, e As EventArgs) Handles btnTEST1.Click
lblTEST1.Text = "Refreshed at " & DateTime.Now.ToString()
End Sub
Protected Sub Button1_Click(sender As Object, e As EventArgs) Handles Button1.Click
Label1.Text = "Refreshed at " & DateTime.Now.ToString()
End Sub
Testing the issue
Click on all 3 of the divs with the "Click Me" text so that HTML is altered inside and outside of the UpdatePanels.
Click one of the buttons labeled "AsyncPostBack". Regardless on which one is clicked, both UpdatePanels will have their HTML rerendered and replaced, as seen by the 2 divs inside the UpdatePanels resetting to their original text.
So I ask, is it possible to have multiple UpdatePanels on the same page that don't cause each other to rerender every time one of them has a asyncPostBack event.
yes
set updatemode=conditional
provide the triggers which will trigger the update. here is a link to an example. (#1 result on google) http://ajax.net-tutorials.com/controls/updatepanel-control/
Try adding mode to update panel tag. If mode is not give the default mode is always. If the UpdateMode property is Always, the UpdatePanel control's content is updated on every postback that originates from anywhere on the page. Microsoft documentation about UpdateMode
<asp:UpdatePanel ID="BugsListUpdatePanel" runat="server" UpdateMode="Conditional">

Sys.WebForms.PageRequestManagerServerErrorException: An unknown error occurred

while trying to process some user input which contains characters such as <.
I do want to sanitize this input and allow it to be displayed and be XSS safe.
I'm getting this ajax error even though I haven't reached the the vb code behind to clean up the input.
Sys.WebForms.PageRequestManagerServerErrorException: An unknown error occurred while processing the request on the server. The status code returned from the server was: 500
The input is controlled by a btnNoteSave which is a updatepanel trigger.
<div style="width: 100%; float: left">
<div>
<asp:Button ValidationGroup="valgroup1" ID="btnNoteSave" runat="server" Text="Save"
class="ui-state-default ui-corner-all float-left ui-button" />
</div>
</div>
<div style="width: 100%; float: left">
<asp:UpdatePanel ID="pnlNotes" runat="server">
<ContentTemplate>
<div id="content_container" style="margin-top: 85px">
<asp:Label ID="lblNotes" runat="server"></asp:Label>
</div>
</ContentTemplate>
<Triggers>
<asp:AsyncPostBackTrigger ControlID="btnNoteSave" EventName="click" />
</Triggers>
</asp:UpdatePanel>
</div>
I've tried sanitizing my input in the code behind but I'm not even reaching that far. The error is an ajax error that throws when it reaches here.
Protected Sub btnNoteSave_Click(ByVal sender As Object, ByVal e As System.EventArgs) Handles btnNoteSave.Click
....
newnote.Note = Server.HtmlEncode(txtNote.Text)
....
End Sub
Any ideas how to get deal with these issues?
Thanks,
You probably need to add ValidateRequest="false" to the #Page directive of your page (or to the <pages> element in your web.config file. This disables XSS checking by ASP.NET that is triggered when it encountered < > characters.
If you are still getting 500 errors from the PageRequestManager try temporarily moving the controls outside of the UpdatePanel so you can better inspect the runtime error.

Resources