ASP.NET、jQuery、脏表单和window.onbeforeunload
在我的ASP.NET web应用程序中,我试图创建一种通用的方法,在用户进行更改之前,使用jQuery警告他们离开表单。相当标准的东西,但经过大量的搜索,我还没有找到一种有效的技术 以下是我目前的情况:ASP.NET、jQuery、脏表单和window.onbeforeunload,asp.net,jquery,onbeforeunload,Asp.net,Jquery,Onbeforeunload,在我的ASP.NET web应用程序中,我试图创建一种通用的方法,在用户进行更改之前,使用jQuery警告他们离开表单。相当标准的东西,但经过大量的搜索,我还没有找到一种有效的技术 以下是我目前的情况: addToPostBack = function(func) { var old__doPostBack = __doPostBack; if (typeof __doPostBack != 'function') { __doPo
addToPostBack = function(func) {
var old__doPostBack = __doPostBack;
if (typeof __doPostBack != 'function') {
__doPostBack = func;
} else {
__doPostBack = function() {
old__doPostBack();
func();
}
}
}
var isDirty = false;
$(document).ready(function() {
addToPostBack(function() {
alert("Postback detected.")
clearDirty();
});
$(':input').bind("change select keydown", setDirty);
window.onbeforeunload = function(e) {
var msg = "You have unsaved changes. "
if (isDirty == true) {
var e = e || window.event;
if (e) { e.returnValue = msg; }
return msg;
}
};
});
setDirty = function() {isDirty = true;}
clearDirty = function() {isDirty = false;}
这可以警告用户不要离开。问题是我在每次回发的同一页上都会收到警告。我的表单上有很多东西可能会触发回发:
onbeforeunload
在doPostBack之前触发,显然是因为IE在单击链接时立即触发onbeforeunload()
当然,我可以连接这些控件以清除isDirty位,但我更喜欢在表单级别操作的解决方案,它不需要我接触可能触发回发的每个控件
是否有人有一种方法可以在ASP.NET中工作,并且不涉及连接可能导致回发的每个控件?您可以始终创建一个继承的页面类,该类具有一个自定义的
OnLoad
/OnUnload
方法,该方法添加到即时执行JavaScript中
然后,您不必在特定于控件的级别上处理它,而是在表单/页面级别上处理它。很有趣,但是。。。为什么不使用jQuery做所有事情
var defaultSubmitControl = false;
var dirty = false;
$(document).ready(function( ) {
$('form').submit(function( ) { dirty = false });
$(window).unload(function( ) {
if ( dirty && confirm('Save?') ) {
__doPastBack(defaultSubmitControl || $('form :submit[id]').get(0).id, '');
}
});
});
···
dirty = true;
···
现在,如果这仍然导致相同的问题(unload
在submit
之前触发),您可以尝试另一个事件树,而不是直接调用\u doPostBack
)
setTimeout(function( ) {
__doPastBack(defaultSubmitControl || $('form :submit[id]').get(0).id, '');
}, 1); // I think using 0 (zero) works too
我还没有尝试过,这是我的想法,但我认为这可能是一种解决方法。我也在考虑这个问题,但到目前为止我发现的是,一种使用所有html控件而不是asp.net web控件的解决方案,你想过吗
<script type="text/javascript">
$(document).ready(function () {
$("form").dirty_form();
$("#btnCancel").dirty_stopper();
});
</script>
$(文档).ready(函数(){
$(“形式”).dirty_form();
$(“#btnCancel”).dirty_stopper();
});
基本上是通过跟踪鼠标位置实现的。请记住,您仍然可以获得Y值的正值(因此我的代码<50行),但只要提交按钮向下超过100像素,就可以了
下面是我添加的Javascript,用于跟踪鼠标更改并捕获onbeforeunload事件:
<script language="JavaScript1.2">
<!--
// Detect if the browser is IE or not.
// If it is not IE, we assume that the browser is NS.
var IE = document.all?true:false
// If NS -- that is, !IE -- then set up for mouse capture
if (!IE) document.captureEvents(Event.MOUSEMOVE)
// Set-up to use getMouseXY function onMouseMove
document.onmousemove = getMouseXY;
// Temporary variables to hold mouse x-y pos.s
var tempX = 0
var tempY = 0
// Main function to retrieve mouse x-y pos.s
function getMouseXY(e) {
if (IE) { // grab the x-y pos.s if browser is IE
tempX = event.clientX + document.body.scrollLeft
tempY = event.clientY + document.body.scrollTop
} else { // grab the x-y pos.s if browser is NS
tempX = e.pageX
tempY = e.pageY
}
// catch possible negative values in NS4
if (tempX < 0){tempX = 0}
if (tempY < 0){tempY = 0}
// show the position values in the form named Show
// in the text fields named MouseX and MouseY
document.Show.MouseX.value = tempX
document.Show.MouseY.value = tempY
return true
}
//-->
</script>
<script type="text/javascript">
window.onbeforeunload = HandleOnClose;
function HandleOnClose(e) {
var posY = 0;
var elem = document.getElementsByName('MouseY');
if (elem[0]) {
posY = elem[0].value;
}
if (posY < 50) { // Your form "submit" buttons will hopefully be more than 100 pixels down due to movement
return "You have not selected an option, are you sure you want to close?";
}
}
</script>
window.onbeforeuload=HandleOnClose;
功能关闭(e){
var-posY=0;
var elem=document.getElementsByName('MouseY');
if(元素[0]){
posY=elem[0]。值;
}
如果(posY<50){//由于移动,您的表单“提交”按钮有望减少100多个像素
return“您尚未选择选项,是否确实要关闭?”;
}
}
然后,只需在页面上添加以下表单:
<form name="Show">
<input type="hidden" name="MouseX" value="0" size="4">
<input type="hidden" name="MouseY" value="0" style="display:block" size="0">
</form>
就这样!它可能需要一些清理(删除MouseX等),但这在我现有的ASP.NET3.5应用程序中起作用,我想我会发布文章来帮助任何人。适用于IE 7和Firefox 3.6,还没有试用过Chrome。我在谷歌上搜索MVC的解决方案时发现了这篇文章。这个解决方案,从赫伯的上述改编,似乎工作得很好。因为MVC对此没有什么特别之处,所以它应该同样适用于PHP、经典ASP或任何其他使用HTML和JQuery的应用程序
var isDirty = false;
$(document).ready(function () {
$(':input').bind("change select keydown", setDirty);
$('form').submit(clearDirty);
window.onbeforeunload = function (e) {
var msg = "You have unsaved changes. "
if (isDirty == true) {
var e = e || window.event;
if (e) { e.returnValue = msg; }
return msg;
}
};
});
setDirty = function () { isDirty = true; }
clearDirty = function () { isDirty = false; }
你可以作弊并检查SO源代码,看看它们做了什么。SO在卸载前使用,但MVC==无回发==没有Herb的特殊问题。不清楚你的建议是什么。这个方法会做什么?