i am printing a gridview in asp.net that is contained within a panel - it works in IE perfectly
In Opera 12.02 it appears to be printing out my main form not the print page ? Do you know why this is.
In Mozilla firefox 16.0.2 it only loads one page in the print preview and prints that one page? Do you know why this is?
I'm assuming the issue is in my javascript - i can post markup if needed but hopefully that will not be required.
thanks
Damo
javascript
<script type="text/javascript">
function PrintGridData(GridToPrint, PanelName) {
try {
var Grid = document.getElementById(GridToPrint);
var printContent = document.getElementById(PanelName);
//alert(printContent);
if (Grid) // See if the Grid Exists First
{
if (Grid.rows.length > 0) { // See if the Grid contains any rows
var windowUrl = 'about:blank';
var UserLoggedIn = $("#lblUser").text()
var now = new Date();
var strDateTime = [[AddZero(now.getDate()), AddZero(now.getMonth() + 1), now.getFullYear()].join("/"), [AddZero(now.getHours()), AddZero(now.getMinutes())].join(":"), now.getHours() >= 12 ? "PM" : "AM"].join(" ");
var Database = 'ProductionDatabase';
var windowName = 'Report';
var AuditPrintDetailEverypage = UserLoggedIn + ' Time : ' + strDateTime ;
var AuditPrintDetailLastPage = ' System Report ' + ' Source Database: ';
var WinPrint = window.open(windowUrl, windowName, 'left=300,top=300,right=500,bottom=500,width=1000,height=500');
WinPrint.document.write('<' + 'html' + '><head><link href="assets/css/Print.css" rel="stylesheet" type="text/css" /><title>' + AuditPrintDetailEverypage + '</title> </head><' + 'body style="background:none !important"' + '>');
WinPrint.document.write(printContent.innerHTML);
WinPrint.document.write(' ' + AuditPrintDetailLastPage);
WinPrint.document.write('<' + '/body' + '><' + '/html' + '>');
WinPrint.document.close();
//alert(printContent.innerHTML);
//alert(WinPrint.document);
if (window.opera) {
//alert('opera browser detected')
window.onload = window.print();
//window.onload = WinPrint.print();
//WinPrint.close();
}
else {
WinPrint.focus();
WinPrint.print();
WinPrint.close();
}
}
else { // No Results to print
document.getElementById('lblErrorCode').innerHTML = '-1';
document.getElementById('lblErrorMessage').innerHTML = 'You have no Results to print. Please run a report.';
document.getElementById('lblExMessage').innerHTML = '-1';
var modal = $find("modalPopupExtenderError");
modal.show();
}
}
else { // No Grid to print
document.getElementById('lblErrorCode').innerHTML = '-1';
document.getElementById('lblErrorMessage').innerHTML = 'You have no Grid to print. Please run a report.';
document.getElementById('lblExMessage').innerHTML = '-1';
var modal = $find("modalPopupExtenderError");
modal.show();
return;
}
}
catch (err) {
//alert(err);
document.getElementById('lblErrorCode').innerHTML = '-1';
document.getElementById('lblErrorMessage').innerHTML = err;
document.getElementById('lblExMessage').innerHTML = '-1';
var modal = $find("modalPopupExtenderError");
modal.show();
return;
}
}
function AddZero(num) {
try {
return (num >= 0 && num < 10) ? "0" + num : num + "";
}
catch (err) {
//alert(err);
document.getElementById('lblErrorCode').innerHTML = '-1';
document.getElementById('lblErrorMessage').innerHTML = err;
document.getElementById('lblExMessage').innerHTML = '-1';
var modal = $find("modalPopupExtenderError");
modal.show();
return;
}
}
</script>
window.onload = window.print(); should be window.onload = window.print;
Also my css had overflow: hidden; which opera and mozilla dont like so i removed these
now its working ok
thanks
damo
Related
First attempt at this: I created the Windows Media Player programmatically by adding the WMPLib as a reference in my project. I am trying to play a playlist using Windows Media Player in a ASP.Net web page (Visual Studio 2015). I cannot use the video tag used in examples for HTML 5 as I need to display .wmv, .mp4, .jpg formats in the control. When I run the code, no errors are displayed and I see an empty browser, what am I missing?
Here is my sample code:
WMPLib.WindowsMediaPlayer Player;
protected void Page_Load(object sender, EventArgs e)
{
FileNames();
}
public void FileNames()
{
String[] extentions = { "*.wmv", "*.mp4", "*.jpg" };
List<string> files = new List<string>();
foreach (string filter in extentions)
{
files.AddRange(System.IO.Directory.GetFiles(#"C:\Documents\", filter));
}
foreach (string ss in files)
{
String name = System.IO.Path.GetFileName(ss);
Player = new WMPLib.WindowsMediaPlayer();
WMPLib.IWMPPlaylist playList = Player.newPlaylist("myPlayList", "");
playList.appendItem(Player.newMedia(name));
Player.currentPlaylist = playList;
Player.controls.play();
}
}
I am aware of the hard coded path which is not good practice, however I just need to get this displaying on my local machine.
Thanks!
After two more weeks of research we managed to come up with a solution by toggling between different types of controls based on the content that needs to be displayed. To display PowerPoint slideshows, we converted all slides to images and then looped through the collection. Here is a snippet of the code in case someone else needs a bit of guidance with a similar issue:
<body>
<form id="form1" runat="server">
<%-- Video DIV --%>
<div runat="server" id="VidDiv" class="fullscreen-bg">
</div>
<%-- IMAGE DIV --%>
<div runat="server" id="container">
<div runat="server" id="containers">
</div>
<%-- this is where the code gets dynamically created --%>
</div>
</form>
</body>
<script src="Scripts/jquery-3.1.1.js"></script>
<script id="CallMyFunction" type="text/javascript">
var index = 1;
document.getElementById("VidDiv").style.display = "none";
var ImageCount = 1;
autoSlide();
function autoSlide() {
var x = document.getElementsByClassName("Images");
var video_player = document.getElementsByClassName("fullscreen-bd__video");
var count;
var video;
var videoSource = new Array(), vids, i;
for (i = 0; i < x.length; i++) {
x[i].style.display = "none";
}
if (index > x.length) {
index = 1
}
x[index - 1].style.display = "block";
count = x.length;
if (ImageCount <= count) {
index++;
ImageCount = 1 + ImageCount;
setTimeout(autoSlide, 8000);
}
else {
//this is where we should switch from image div to video div
document.getElementById("container").style.display = "none";
document.getElementById("VidDiv").style.display = "block";
//create a counter to check the number of video tags
video = document.getElementsByTagName('video'), numVideos = video.length;
for (i = 0; i < numVideos; i++) {
videoSource[i] = video.item(i).src;
document.getElementById("myVideo" + i).style.display = "none";
}
var videoCount = 0;
if (videoCount <= numVideos -1) {
function videoPlay(videoNum) {
if (videoCount > 0)
{
document.getElementById("myVideo" + (videoCount - 1)).style.display = "none";
}
document.getElementById("myVideo" + videoCount).style.display = "block";
document.getElementById("myVideo" + videoCount).setAttribute("src", "" + videoSource[videoCount] + "");
document.getElementById("myVideo" + videoCount).load();
document.getElementById("myVideo" + videoCount).play();
onEndedVid = document.getElementById("myVideo" + videoCount);
var onEndedVid;
onEndedVid.onended = function () {
//at the end of the video, close full screen
myHandler();
};
videoCount = videoCount + 1;
}
function myHandler() {
if (videoCount == numVideos) {
//this is where we should switch from image div to video div
document.getElementById("container").style.display = "none";
document.getElementById("VidDiv").style.display = "none";
location.reload();
}
else {
videoPlay(videoCount);
}
}
myHandler();
}
else
{
///back to images
//refresh the page
location.reload();
}
}
}
Code behind:
// this will be a watcher that checks if is new content... if there is, delete the existing .wpl file and recreate the .wpl with new content links included
private void CreateNewPlayList(string folder)
{
try
{
System.Threading.Thread.Sleep(5000);
fileName = getDrive(folder) + #"\" + folder + "Playlist.wpl";
FileInfo fileInfo = new FileInfo(fileName);
String f = #"<?wpl version=""1.0""?>
<smil>
<head><meta name=""Generator"" content=""Microsoft Windows Media
Player -- 10.0.0.3646""/>
<author/>
<title> a title goes here </title>
</head>
<body>
<seq> ";
String ff = #"
</seq>
</body>
</smil>";
using (FileStream fs = fileInfo.Create())
{
Byte[] txt = new UTF8Encoding(true).GetBytes(f);
fs.Write(txt, 0, txt.Length);
////write paths and load only certain file types according to requirements into array
String[] extentions = { "*.mp4", "*.wmv", "*.JPG".ToLower(), "*.ppt", "*.png" };
List<string> files = new List<string>();
foreach (string filter in extentions)
{
files.AddRange(System.IO.Directory.GetFiles(getDrive(folder) + #"\", filter));
}
int filecount = files.Count;
string[] video_lists = new string[files.Count];
int counts = 0;
foreach (string file in files)
{
video_lists[counts] = file.ToString();
string PathfileName = Path.GetFileName(file);
Byte[] author;
//use the ppt to be able to go into the folder and add each slide as part of the playlist
if (Path.GetExtension(PathfileName) == ".ppt" || Path.GetExtension(PathfileName) == ".pptx")
{
//create a loop to loop through the folder that has the same name as ppt/pptx(PathFileName)
string pptDrive = getDrive(folder) + #"\" + Path.GetFileNameWithoutExtension(PathfileName) + #"\";
if (Directory.Exists(pptDrive))
{
string[] pptFilesFolder = Directory.GetFiles(pptDrive);
int counter = 1;
while (counter <= pptFilesFolder.Length)
{
foreach (string pptFile in pptFilesFolder)
{
string pptFileName = Path.GetFileName(pptFile);
string pptFileNameNoExt = Path.GetFileNameWithoutExtension(pptFile);
int i = pptFilesFolder.Length;
int ss = Convert.ToInt16(new String(pptFileNameNoExt.Where(Char.IsDigit).ToArray()));
if (ss <= i && ss == counter)
{
author = new UTF8Encoding(true).GetBytes(#"<media src=""" + pptDrive + #"\" + pptFileName + "\"/>");
fs.Write(author, 0, author.Length);
counter++;
}
}
}
}
else
{
//do something...
}
}
else
{
author = new UTF8Encoding(true).GetBytes(#"<media src=""" + getDrive(folder) + #"\" + PathfileName + "\"/>");
fs.Write(author, 0, author.Length);
}
counts = counts + 1;
}
Byte[] toptxt = new UTF8Encoding(true).GetBytes(ff);
fs.Write(toptxt, 0, toptxt.Length);
}
}
catch (IOException io)
{
//error handling....
return;
}
catch (Exception ex)
{
//error handling...
return;
}
}
The code can obviously be improved and optimized, but this is the base we used to get our app working. Thanks for all the advice and input!
I have a .net page which needs to open a new pop-up window when certain conditions are not met in the code behind file. I have the following code:
private bool isValidPart(string partNo)
{
if (!string.IsNullOrEmpty(partNo))
{
DataBase.DBManager dm = new DBManager();
if (!Convert.ToBoolean(dm.ExecScalar("usp_getPart", partNo)))
{
string url = "test.aspx";
string s = "window.open('" + url + "', 'popup_window', 'width=300,height=100,left=100,top=100,resizable=yes');";
ClientScript.RegisterStartupScript(this.GetType(), "script", s, true);
return false;
}
}
return true;
}
I put a break point and verified it. It hits the line but the pop-up window does not open up. It just simply moves to next line and returns false.
May I please know the reason behind it?
#yog2411 This is the code which checks that isvalidpart()
private bool SetRowData()
{
int rowIndex = 0;
if (ViewState["CurrentData"] != null)
{
DataTable dtCurrentData = (DataTable)ViewState["CurrentData"];
DataRow drCurrentRow = null;
if (dtCurrentData.Rows.Count > 0)
{
for (int i = 1; i <= dtCurrentData.Rows.Count; i++)
{
TextBox TextCustomerName = (TextBox)gvInventory.Rows[rowIndex].Cells[1].FindControl("txtCustomerName");
TextBox TextPONumber = (TextBox)gvInventory.Rows[rowIndex].Cells[2].FindControl("txtPONumber");
TextBox TextPartNumber = (TextBox)gvInventory.Rows[rowIndex].Cells[3].FindControl("txtPartNumber");
TextBox TextQuantity = (TextBox)gvInventory.Rows[rowIndex].Cells[4].FindControl("txtQuantity");
//TextBox TextReqShipDate = (TextBox)gvInventory.Rows[rowIndex].Cells[5].FindControl("txtReqShipDate");
if (!isValidPart(TextPartNumber.Text))
return false;
drCurrentRow = dtCurrentData.NewRow();
drCurrentRow["RowNumber"] = i + 1;
dtCurrentData.Rows[i - 1]["CustName"] = TextCustomerName.Text;
dtCurrentData.Rows[i - 1]["PONum"] = TextPONumber.Text;
dtCurrentData.Rows[i - 1]["PartNum"] = TextPartNumber.Text;
dtCurrentData.Rows[i - 1]["Qty"] = TextQuantity.Text;
// dtCurrentData.Rows[i - 1]["ReqShipDate"] = TextReqShipDate.Text;
rowIndex++;
}
ViewState["CurrentData"] = dtCurrentData;
gvInventory.DataSource = dtCurrentData;
gvInventory.DataBind();}
}
SetPreviousData();
return true;
}
try writing a JS function
function showMyPopUp(myUrl) {
//I have this settings and it works like a popUp,
//I just going to write the properties you have, but you can change them for these ones
//var CustomFeatures = 'titlebar=no, status=no,menubar=no,resizable=no,scrollbars=no,toolbar=no,location=no,width=300,height=100,top=100,left=100';
var CustomFeatures = 'resizable=yes,width=300,height=100,top=100,left=100';
window.open(myUrl, '_blank', CustomFeatures, true);
}
and in your C# this
string url = "test.aspx";
string myCallfunction = "showMyPopUp('" + url + "');"
ScriptManager.RegisterStartupScript(this, this.GetType(), "Funct", myCallfunction , true);
hope it helps
I have a dropdownlist and a fileupload control in a panel which is added with other controls in an UpdatePanel. When a value is selected from the dropdown and a file is uploaded, the Upload button is enabled. For this I have a javascript function as follows:
function SetUploadButtonEnabled(controlPanel, fileUploadId) {
var docTypesList = controlPanel.find("select");
var gotListVal = docTypesList.val() != "";
var fileUpload = $find(fileUploadId);
var gotFileVal = fileUpload.getUploadedFiles().length > 0;
var enable = gotListVal && gotFileVal;
if (enable) {
controlPanel.find(".GxButtonBlue").removeAttr("disabled");
}
else {
controlPanel.find(".GxButtonBlue").attr("disabled", true);
}
}
I am trying to call it from code behind as follows, but the function is not being called:
string script = "<script type=\"text/javascript\">"
+ "\n $(document).ready(function (){"
+ "\n $(document).on(\"change\", \"#" + this._DdDocumentTypes.ClientID + "\", function(event){"
+ "\n var docUploadControlPanel = $(this).closest(\"#" + this._DocUploadControlPanel.ClientID + "\");"
+ "\n SetUploadButtonEnabled(docUploadControlPanel, \"" + this._fiInput.ClientID + "\");"
+ "\n });"
+ "\n });"
+ "\n "
+ "</script>";
Page.ClientScript.RegisterClientScriptBlock(this.GetType(), "DocumentAjaxUploadCtrlScript_" + this.ClientID, script);
Since an Update Panel is there I even tried:
ScriptManager.RegisterClientScriptBlock(this.Page, this.GetType(), "DocumentAjaxUploadCtrlScript_" + this.ClientID, script, true);
Please help me find why the function is never called!
Here's one way to do it. The key here is the pageComponents object.
ASPX or User Control
<script>
var pageComponents = {
documentTypeSelector: "#<%= _DdDocumentTypes.ClientID %>",
uploadControlSelector: "#<%= _DocUploadControlPanel.ClientID %>",
fiInputSelector: "#<%= _fiInput.ClientID %>"
};
</script>
JavaScript Place after the above
function SetUploadButtonEnabled(controlPanel, fileUploadId) {
var docTypesList = controlPanel.find("select");
var gotListVal = docTypesList.val() != "";
var fileUpload = $find(fileUploadId);
var gotFileVal = fileUpload.getUploadedFiles().length > 0;
var enable = gotListVal && gotFileVal;
if (enable) {
controlPanel.find(".GxButtonBlue").removeAttr("disabled");
}
else {
controlPanel.find(".GxButtonBlue").attr("disabled", true);
}
}
$(document).ready(function (){
$(document).on("change", pageComponents.documentTypeSelector, function(event){
var docUploadControlPanel = $(this).closest(pageComponents.uploadControlSelector);
SetUploadButtonEnabled(docUploadControlPanel, pageComponents.fiInputSelector);
});
});
Remarks
You can avoid using the "bee sting" syntax above by setting the control ClientIDMode property to Static (assuming you're using only ASP.NET Page, not a user control. Then your JavaScript would look like below:
$(document).ready(function (){
$(document).on("change", "#documentType", function(event){
var docUploadControlPanel = $(this).closest("#uploadControl");
SetUploadButtonEnabled(docUploadControlPanel, "#fiInput");
});
});
In addition the line:
var docUploadControlPanel = $(this).closest(pageComponents.uploadControlSelector);
could be written as:
var docUploadControlPanel = $(pageComponents.uploadControlSelector);
since ClientID always returns a unique element ID for the entire page.
I use C# 4.0 and SQL Server 2008 R2 and I've a simple button click that call a function that save the data into database and redirect the page.
The probleme is when the client click more than one on this save button, then i save more than one item also into the database.
I want to avoid the client make a mistake, that meant the client can only do 1 clic = 1 save data.
<dx:ASPxButton ID="ASPxButton_save" runat="server" Image-Url="~/images/Icon/Good-or-Tick-icon.png" Text="Enregistrer" Width="110px" onclick="ASPxButton_save_Click" ValidationGroup="Savebouton">
</dx:ASPxButton>
protected void ASPxButton_save_Click(object sender, EventArgs e)
{
string ErrPos = "";
try
{
ErrPos = "Affct CP DEST";
string FA_Choisi = ASPxTextBox_CP_dest.Text.Substring(0, 2);
string CLIENT_de_FA = ClientId.Substring(0, 2);
List<string> ClotList_FA = new List<string>();
ErrPos = "Affct Trans";
foreach (DataRow myRow in oOrdre_BL.Get_Tranporteur(ClientId).Tables["Le_Transporter"].Rows)
{
ClotList_FA.Add(myRow["LIBELLE"].ToString());
}
Pers_Client_Entrp oPersclientEntrp = GetOPersclientEntrp();
Pers_Ordre oPersOrdr = new
.......
if (ASPxCheckBox_NewDesti.Checked)
{
string ResTemp = oDest_BL.Compare_Dest(ClientId, ASPxTextBox_Desti_ID.Text, ASPxTextBox_RS_NOM_dest.Text, ASPxTextBox_ADRESSE_dest.Text);
if (!String.IsNullOrWhiteSpace(ResTemp))
{
lbl_err.Text = ResTemp;
}
else
{
Pers_Dest TheDest = new Pers_Dest();
TheDest.CodeDest = ASPxTextBox_Desti_ID.Text.Replace('-', ' ').Replace('\'', ' ');
TheDest.CodeClient = ClientId;
TheDest.RaisonSoc = ASPxTextBox_RS_NOM_dest.Text.Replace('-', ' ').Replace('\'', ' ');
TheDest.Adresse = ASPxTextBox_ADRESSE_dest.Text.Replace('-', ' ').Replace('\'', ' ');
TheDest.Cp = ASPxTextBox_CP_dest.Text;
TheDest.Ville = ASPxComboBox_VILLE_dest.Text;
TheDest.Pays = ASPxComboBox_PAYS_dest.Value.ToString();
TheDest.Tel = ASPxTextBox_TEL_dest.Text.Replace('-', ' ').Replace('\'', ' ');
TheDest.Fax = ASPxTextBox_FAX_dest.Text.Replace('-', ' ').Replace('\'', ' ');
TheDest.Email = ASPxTextBox_EMAIL_dest.Text.Replace('-', ' ').Replace('\'', ' ');
TheDest.Insee = ASPxTextBox_INSEE_dest.Text.Replace('-', ' ').Replace('\'', ' ');
TheDest.Siret = ASPxButton_SIRET_dest.Text.Replace('-', ' ').Replace('\'', ' ');
oDest_BL.CrUp_Dest(TheDest, true);
oPersOrdr.Ville = ASPxComboBox_VILLE_dest.Text;
Save_Part(oPersOrdr, oPersclientEntrp, OrdreID);
}
}
else
{
oPersOrdr.Ville = ASPxTextBox_VILLE_dest.Text.Replace('-', ' ').Replace('\'', ' ');
Save_Part(oPersOrdr, oPersclientEntrp, OrdreID);
}
catch (Exception ex)
{
lbl_err.Text = ex.Message;
if (ex.InnerException != null) { lbl_err.Text += "-->" +ex.InnerException.Message; }
Outils_IHM.SendingEmail("Save Odre --> Err Position: " + ErrPos + "-----" + lbl_err.Text, ClientId);
}
private void Save_Part(Pers_Ordre oPersOrdr, Pers_Client_Entrp oPersclientEntrp, string OrdreID)
{
oOrdre_BL.SaveUpdt_Ordre_BL(oPersOrdr, OrdreID);
string QuelleID = TempId;
if (!String.IsNullOrWhiteSpace(OrdreID))
{ QuelleID = OrdreID; }
if (oPersclientEntrp.TypPrint == "Zebra")
{ Response.Redirect("../Print/BonEticket_Web.aspx?ConnPrint=UnDirect&OdreID=" + QuelleID + "&CountOrdre=" + ASPxTextBox_NBR_COLIS.Text + "&TypeAR=" + TypeEnlev, false); }
else
{ Response.Redirect("../Print/BonEticket_Web.aspx?OdreID=" + QuelleID + "&CountOrdre=" + ASPxTextBox_NBR_COLIS.Text + "&TypeAR=" + TypeEnlev, false); }
Context.ApplicationInstance.CompleteRequest();
}
I have an idea, when the user clic this button, than it will call client side function to disable it. But i don't know how and if it work as i want to.
you can use the below mentioned code as ref.
<html xmlns="http://www.w3.org/1999/xhtml">
<head runat="server">
<title></title>
<script language="javascript" type="text/javascript">
var submit = 0;
function CheckIsRepeat() {
if (++submit > 1) {
alert('An attempt was made to submit this form more than once; this extra attempt will be ignored.');
return false;
}
}
</script>
</head>
<body>
<form id="form1" runat="server">
<div>
<asp:Button ID="Button1" runat="server" Text="Button" onclick="Button1_Click" OnClientClick="return CheckIsRepeat();" />
</div>
</form>
</body>
</html>
Before saving data to database disbale the button , then save the data, then clear the controls & then again enable the button.
<dx:ASPxButton ID="ASPxButton_save" runat="server" Image-Url="~/images/Icon/Good-or-Tick-icon.png" Text="Enregistrer" ClientInstanceName="ASPxButton_save" Width="110px" onclick="ASPxButton_save_Click" ValidationGroup="Savebouton">
<ClientSideEvents Click ="function(s,e) { MyBtnClick(s,e); } " />
</dx:ASPxButton>
function MyBtnClick(s, e) {
if (ASPxClientEdit.AreEditorsValid())
ASPxButton_save.SetVisible(false);
}
Here is my JavaScript:
<script type="text/javascript">
function onholdev(index) {
var chk = document.getElementById('<%=grdCons.Rows[' + index + '].FindControl("chkHold").ClientID %>');
var txt = document.getElementById('<%=grdCons.Rows[' + index + '].FindControl("txtReason").ClientID %>');
if (chk.checked == true) {
txt.disabled = false;
}
else {
txt.disabled = true;
txt.value = "";
}
}
</script>
The 'index' variable comes from the RowDataBound event of my GridView, like so:
CheckBox chkHold = ((CheckBox)e.Row.FindControl("chkHold"));
chkHold.Attributes.Add("onchange", "onholdev(" + e.Row.RowIndex + ")");
However, I'm getting 'too many characters in string literal' in the first line of my function (beginning with var chk). Why is this?
You're mixing client and server-side script...you just can't do this. This is executed server-side:
grdCons.Rows[' + index + '].FindControl("chkHold").ClientID
But you're calling it client-side and trying to pass an ID, that's just not something you can do, look at your rendered JavaScript function and this will be much clearer. Instead just use the ID of the table, then you can find your controls that way, for example:
var row = document.getElementById("grdCons").rows[index];
var inputs = row.getElementsByTagName("input");
//then filter by ID match, class, whatever's easiest and set what you need here
That's probably because ASP.NET throws an error, which is written in the client side call of getElementById. The onholdev function is executed client - side, and so cannot pass the index parameter to ASP.NET which is executed server - side. Try this:
<script type="text/javascript">
function onholdev(checkbox, textbox) {
var chk = document.getElementById(checkbox);
var txt = document.getElementById(textbox);
if (chk.checked == true) {
txt.disabled = false;
}
else {
txt.disabled = true;
txt.value = "";
}
}
</script>
Replacing your server - side code with this:
CheckBox chkHold = ((CheckBox)e.Row.FindControl("chkHold"));
chkHold.Attributes.Add("onchange", "onholdev('" +
e.Row.FindControl("chkHold").ClientID + "','" +
e.Row.FindControl("txtReason").ClientID + "')");
The problem is your use of the single quote characters in ' + index + '. Change those to double qoutes and it should work.