File Upload Control Change Event Not firing - asp.net

I have an asp.net File upload control, I am using Jquery multi file upload with it.
When I select a file, it makes a div under the upload control to display list of files. I want to save the value of upload control in a hidden field, I am using jquery change event on fileupload control but its not firing.
I also tried using same event with the files div, but its also not firing, and no error in Fire Bug.
<asp:FileUpload ID="FileUpload1" runat="server" class="multi" />
<div id="ctl00_ContentPlaceHolder1_FileUpload1" class="MultiFile-list"></div>
$(document).ready(function () {
$("#ctl00_ContentPlaceHolder1_FileUpload1").change(function () {
alert("File Selected");
});
$(".MultiFile-list").change(function () {
alert("File Selected");
});
});
I also tried with div ID, but no luck.

Seems that jQuery don't support multiple file upload very well, but you can try with something like this on the change event:
$("#ctl00_ContentPlaceHolder1_FileUpload1").change(function() {
var files = $('#ctl00_ContentPlaceHolder1_FileUpload1')[0].files;
for (var i = 0; i < files.length; i++) {
$(".MultiFile-list").append(files[i].name);
}
});
As you can read, I get the files list and put the names in the div you defined, just to let you try the code.

Related

ASP.NET using Button instead of FileUpload to upload files

I'm trying to upload a file with Button element using hidden FileUpload element with ASP.NET using this snippet:
protected void Page_Load(object sender, EventArgs e)
{
Button2.Attributes.Add("onclick", "document.getElementById('" + FileUpload1.ClientID + "').click();");
}
My Button has Id = "Button2", FileUpload Id = "FileUpload1". Clicking on the button Windows Explorer opens successfully to upload files but FileUpload.HasFile still returns false in further code (no file gets loaded even though explorer gets opened and file is selected).
What is the cause of this problem and how to fix it?
Well, I suppose you want to hide the the FileUpload Control and still be able to upload the files.
Follow the following steps to achieve the required:
Place a FileUpload Control with the class hidden. Like below:
<style>
.hidden{
display: none;
}
</style>
<asp:FileUpload runat="server" ID="FileUpload1" CssClass="hidden" />
Then place a Button that will be visible to client and will handle the Javascript events
<asp:Button runat="server" ID="Button1" Text="Upload File" OnClick="Button1_Clicked" />
Add the Javascript events to handle things
$(document).ready(function(){
// This event will help click the FileUpload control
$('#<%= Button1.ClientID %>').on('click', function(){
$('#<%= FileUpload1.ClientID %>').click();
return false; // important to return false, so it does not posts back yet.
});
$('#<%= FileUpload1.ClientID %>').on('change', function(){ // To see if the file selection was changed and the user has selected something
if($(this).val() == ''){
alert('No file selected');
return false;
}
if(confirm('Do you want to upload this file? ' + $(this).val())){
__doPostBack('<%= Button1.ClientID %>', ''); // this will postback to the server click event
}
});
});
Now, handle the uploaded file.
public void Button1_Clicked(object sender, EventArgs e)
{
// Handle your upload function
var hasFile = FileUpload1.HasFile;
}
PS: It was a rough Idea, the code is not tested so it might need some love.

upload multiple images using a single file upload control in asp.net web forms

how can I upload multiple images using a single file upload control in asp.net web forms?
I am able to upload a single image file using file upload control but I want to make it more dynamic to upload multiple images by using one control.
Can anyone help me out in this?
Thankyou.
You need to use AllowMultiple attribute, like this
<asp:FileUpload id="controlID" runat="server" AllowMultiple="true"/>
You can't. It is strictly one file per control.
To upload multiple files using one submit button you would need to use Javascript to add more FileControls dynamically, like this (using jQuery):
$(document).ready(function () {
$("#addAnotherFile").click(function () {
$("input[type='file']").after('<br /><input type="file" name="file" />');
}
});
In the submit button handler, you can then enumerate through the Request.Files collection to access your uploads:
for (int i = 0; i < Request.Files.Count; i++)
{
HttpPostedFile file = Request.Files[i];
if (file.ContentLength > 0)
{
file.SaveAs(Path.Join("Uploaded/Files/Path",Path.GetFileName(file.FileName)));
}
}

Where to place the javascript code for content page in ASP.NET when using the master page

I want to use a image slider in my web page, the problem is that when I use the JS code with the master page it doesn't work, it works for page without master page. I tried placing the JS code in master page head section and in the content page in
, neither works.
I am using below js code.
<script language="javascript" type="text/javascript">
var i = 1;
function fun() {
i++;
document.getElementById("img1").src = "images/" + i + ".jpg";
if (i == 4) //here 2 is number of images i want to display in the slide show
{ i = 0; }
}
setInterval("fun()", 2000);
</script>
asp:Image I am almost sure that your problem is with the ids.
Master Page implements the INamingContainer interface, so Controls inside a Page with a Master Page are rendered with a nested id. Something like:
<img name="ctl00$MainContent$img1" id="ctl00_MainContent_img1" />
against what you get in a Page without Master Page
<img name="img1" id="img1" />
It is done this way to guarantee the ids of the controls to be unique within an entire application.
Any control that implements this interface creates a new namespace in which all child control ID attributes are guaranteed to be unique within an entire application. The marker provided by this interface allows unique naming of the dynamically generated server control instances within the Web server controls that support data binding.
You can get the ClientID of a control in Page with the ClientID property.
Your code will look something like:
<script language="javascript" type="text/javascript">
var i = 1;
function fun() {
i++;
document.getElementById("<%= img1.ClientID %>").src = "images/" + i + ".jpg";
if (i == 4) //here 2 is number of images i want to display in the slide show
{ i = 0; }
}
setInterval("fun()", 2000);
</script>
<asp:Image ID="img1" runat="server" />
You can also can set the ClientIDMode of your control to Static when declaring it and it will keep the id you assigned:
<script language="javascript" type="text/javascript">
var i = 1;
function fun() {
i++;
document.getElementById("img1").src = "images/" + i + ".jpg";
if (i == 4) //here 2 is number of images i want to display in the slide show
{ i = 0; }
}
setInterval("fun()", 2000);
</script>
<asp:Image ID="img1" runat="server" ClientIDMode="Static" />
But be warned that you have to do all the work to assure that the ids are not duplicated if you use this last method.
It does not worki because probably the ID of the control you are trying to get using getElementById is different when it get rendered on the page.
more info here
I would not use this approach anyway because you could have cross-browser issue.
I would use a JQuery plug-in instead
When you use masterpage, all aspxcontrols name change (when it get rendered)
if you wanna reach some controls, you have to use controlname.ClientID

JQuery / ASP.NET newbie questions about <asp:Button>

Hey all, having an issue getting asp buttons to interact with JQuery. I'm basically trying to hide a div that contains a form and replace it with an processing image. It works fine for me when I use an HTML input button as the trigger but when I use an aspButton nothing happens.
This works (the id of the HTML button is 'btnSubmit'):
<script>
$('#btnSubmit').click(function () {
$('#form1').fadeOut('fast', function () {
$('#processing').fadeIn('fast', function () {
});
});
});
</script>
This doesn't (the id of the ASP button is 'btnSubmitASP'):
<script>
$('#btnSubmitASP').click(function () {
$('#form1').fadeOut('fast', function () {
$('#processing').fadeIn('fast', function () {
});
});
});
</script>
Any idea what the trick is to get the asp button to do this?
Thanks
The ASP.net server ID for the control is different from the html ID. (ASP.net calls this the client ID). You can get the client id this way:
$('#<%= this.btnSubmitASP.ClientID %>').click( /* etc */ );
If you are using asp.net 4.0 you can set the button's ClientIDMode property ='Static'. This will stop the runtime from mucking with the ID.
Try this:
<script>
$('<%=btnSubmitASP.ClientID%>').click(function () {
$('#form1').fadeOut('fast', function () {
$('#processing').fadeIn('fast', function () {
});
});
});
</script>
Explanation:
ASP.NET renames all of its controls when they get sent to the client. Consequently, your ASP.NET Button does not have a client ID of "btnSubmitASP" client-side. The above code calls the server control on the server side and gets its client-id to use in the jQuery code.
Alternatively, you can use jQuery selectors:
<script>
$("[id$='_btnSubmitASP']").click(function () {
$('#form1').fadeOut('fast', function () {
$('#processing').fadeIn('fast', function () {
});
});
});
</script>
This will look for controls whose client ID ends with "_btnSubmitASP".
Another alternative to using the ClientId is to assign a unique class to the ASP:button. Your selector would then look like this:
<asp:button runat="server" CssClass="submitbutton">/<asp:button>
<script>
$("submitbutton").click(function () {
$('#form1').fadeOut('fast', function () {
$('#processing').fadeIn('fast', function () {
});
});
});
</script>
For ASP.NET buttons you should use the OnClientClick property as it has built in client side scripting added to the button to do its post back behavior. Example:
<asp:Button ID="btnSubmitASP" runat="server"
OnClientClick="yourJqueryFunction();" />
If you return false in the OnClientClick you will prevent the default behavior of the button preventing a PostBack. Doing nothing or returning true will cause the PostBack to occur. By using this method you don't need to know the name of your Button to attach the script code.
To just get your code working though, you need to get the ClientID of the control inline to creating you script so change the following line to use the ClientID property of the Button:
$('#<%= btnSubmitASP.ClientID %>').click(function () {
You need to get the ClientID because ASP.NET adds to name to namespace it and prevent duplication of names. If you look at the ASP.NET Button, the you will notice the name and ID properties have a lot more added to it like:
<input type="submit" name="ctl00$ContentPlaceHolder1$btnSubmitASP" value="Test"
id="ctl00_ContentPlaceHolder1_btnSubmitASP" />
My knowledge of jQuery is very shallow, but I can give you one tip: Remember that jQuery is being executed client-side, while the ASP button is rendered on the server and returned in the response.
Double-check the HTML markup for the button when your page is returned from the server, and make sure it's structured as you expect. Perhaps the ID attribute isn't being set as expected, for example.
Your button controller is runat="server" so this means that .NET will modify the controller's id before rendering it in HTML.
jQuery tries to use that ID to do whatever you want to do with it. But the ID is no longer the same.
Use a class instead on your button. I know it's not as fast as an ID, but it's the best way to do it because .NET will not modify your css class.
If your ASP:Button contains runat="server" then .NET will modify the ID value before it get to the DOM, so your resulting <input> will probably wind up looking like
<input id="ctl00_ContentPlaceHolder1_btnSubmitASP" />
Therefore, your jQuery selector $('#btnSubmitASP') is no longer valid because the ID has changed.
Use Firebug or Right click -> View source to confirm the actual ID value.

How to capture 'Update' click event in ASP.NET GridView with jQuery

I need to capture the 'Update' click event with jQuery in an asp.net GridView and have no way of knowing where to start. I'm still rather new to jQuery. My GridView is attached to a SQLDataSource and, naturally, has all the bells and whistles that that combination affords. Any help would be greatly appreciated.
Simply add the script block anywhere after the GridView is declared and it should work with the default non-templated GridView column. No code in the codebehind as it is purely a Javascript solution.
Use this if you are using a Link-type GridView column:
<script type="text/javascript">
// a:contains(The text of the link here)
$('#<%= theGridViewID.ClientID %> a:contains(Update)').click(function () {
alert('Update click event captured from the link!');
// return false: stop the postback from happening
// return true or don't return anything: continue with the postback
});
</script>
Use this if you are using a Button-type GridView column and you don't want your Javascript to block the postback:
<script type="text/javascript">
// :button[value=The text of the button here]
$('#<%= theGridViewID.ClientID %> :button[value=Update]').click(function () {
alert('Update click event captured from the button!');
});
</script>
Use this if you are using a Button-type GridView column and you want to have control whether to continue with the postback or not:
<script type="text/javascript">
// :button[value=The text of the button here]
var updateButtons = $('#<%= theGridViewID.ClientID %> :button[value=Update]');
updateButtons
.attr('onclick', null)
.click(function () {
alert('Update click event captured from the button!');
var doPostBack = true; // decide whether to do postback or not
if (doPostBack) {
var index = updateButtons.index($(this));
// 'Update$' refers to the GridView command name + dollar sign
__doPostBack('<%= theGridViewID.UniqueID %>', 'Update$' + index);
}
});
</script>
Update: I think this would be a better solution in replacement of the last (3rd) script block I presented above, since you won't need to update the __doPostBack function call manually based on the command name, and as such, it should be less error-prone:
<script type="text/javascript">
// :button[value=The text of the button here]
var updateButtons = $('#<%= theGridViewID.ClientID %> :button[value=Update]');
updateButtons.each(function () {
var onclick = $(this).attr('onclick');
$(this).attr('onclick', null).click(function () {
alert('Update click event captured from the button!');
var doPostBack = true; // decide whether to do postback or not
if (doPostBack) {
onclick();
}
});
});
</script>
Credit to Aristos for this idea. :)
Ok here is my solution to capture only one update (or more) from a button.
This is the javascript code that I run on update click
<script type="text/javascript">
function NowRunTheUpdate(){
alert("ok I capture you");
}
</script>
and here is the page code
`<asp:GridView ID="MyGridView" runat="server" OnRowDataBound="MyGridView_RowDataBound" ... >`
<asp:ButtonField Text="update" CommandName="Update" ButtonType="Button" />
...
Here is the code thats run behind and set the javascript.
protected void MyGridView_RowDataBound(object sender, GridViewRowEventArgs e)
{
if (e.Row.RowType == DataControlRowType.DataRow)
{
// loop all data rows
foreach (DataControlFieldCell cell in e.Row.Cells)
{
// check all cells in one row
foreach (Control control in cell.Controls)
{
// I go to get the button if exist
Button button = control as Button;
if (button != null && button.CommandName == "Update")
// Add delete confirmation
button.OnClientClick = "NowRunTheUpdate();";
}
}
}
}
You need to attach a client-side event listener to the click event of the Update [link]button. I don't think it can be done using AutoGenerateEditButton="true" if you are doing it that way. You'll need to use a TemplateField so that you can manipulate the button. Then you can use jQuery to bind to the click event of the button.
Add the update column to the column templates. Convert it to a custom column, and modify it in such a way you can hook to it with jquery i.e. like adding a css class to it.
Gridview is nothing but a table with a bunch of "tr" and "td". If you understand that concept then it would be easy for you to handle anything at client side. If you have enabled auto everything then it will be a link which would result for Edit, Delete, Update or Cancel (Check View Source). The code given below should capture the update click event:
$("a:contains(Update)").live("click", function() {
//alert("hi"); do what needs to be done
return false;//would not sent the control back to server
});
HTH

Resources