Javascript jqueryajax";“撤消辅助对象”;
基于AJAX的UI中的常见模式是,当用户执行一个动作时,它会立即反映在UI中,但在到达AJAX响应确认一切正常之前,它会被标记为未完成。这就是在Google日历中添加事件的工作方式。当出现错误时,该临时UI更改将恢复 现在,手动执行这样的恢复不是很有创意,所以我怀疑jQuery中有一些“撤销助手”,它允许保留UI元素的状态,然后恢复它——类似于属性堆栈之类的东西。这甚至与AJAX没有任何关系Javascript jqueryajax";“撤消辅助对象”;,javascript,jquery,Javascript,Jquery,基于AJAX的UI中的常见模式是,当用户执行一个动作时,它会立即反映在UI中,但在到达AJAX响应确认一切正常之前,它会被标记为未完成。这就是在Google日历中添加事件的工作方式。当出现错误时,该临时UI更改将恢复 现在,手动执行这样的恢复不是很有创意,所以我怀疑jQuery中有一些“撤销助手”,它允许保留UI元素的状态,然后恢复它——类似于属性堆栈之类的东西。这甚至与AJAX没有任何关系 有类似的情况吗?在这种情况下,我总是发现状态机是一种可行的方法。设计页面/JavaScript时,您可以
有类似的情况吗?在这种情况下,我总是发现状态机是一种可行的方法。设计页面/JavaScript时,您可以在任何时候指定一组输入,并且在整个页面上始终获得相同的输出。这种方法的好处在于,你不知道你是如何到达你在程序中的位置的,你只需要知道是什么数据导致了当前状态 对于您的情况,您可以创建一个基本对象来描述您的状态:
var state = { user: 'Tomasz', ajaxSent: false, otherState: 123 };
function updateFromState(state){
// Set all dependent UI visibilities, etc. based on state object
}
然后,在进行任何更改之前,将当前状态推送到阵列上,以便在需要时恢复:
var stateList = [];
stateList.push({ user: 'Tomasz', ajaxSent: false, otherState: 123 });
// Do something that changes your state
var newState = {user: 'Tomasz', ajaxSent: true, otherState: 123 };
updateFromState(newState);
// Now, if you need to revert
var previousState = stateList.pop();
updateFromState(previousState);
这种方法的缺点是,您实际上并没有“撤销”您可能调用的任何副作用。例如,如果您制作了一篇修改服务器上数据的AJAX文章,那么您必须了解如何“撤销”该AJAX文章。这不仅仅是更改页面的本地状态。但是,如果您不需要撤消服务器端影响,而只需要能够准确地反映页面的正确状态,这可能对您有用
如果我正在做这样的事情,我可能会使用以下方法开始:
var StateHelper = function(){
var stateList = [];
var callbacks = [];
this.onChange = function(callback){
callbacks.push(callback);
};
this.set = function(opts){
stateList.push(opts);
apply(opts);
};
this.undo = function(){
if(stateList.length <= 1){
return; // nothing to undo
}
// To undo, we go back 2, since top of stack is current
stateList.pop();
var last = stateList[stateList.length - 1];
apply(last);
};
var apply = function(opts){
var length = callbacks.length;
for(var i = 0; i < length; i++){
callbacks[i](opts);
}
};
};
<div id='title' style='text-decoration: underline;'>some title</div>
<div id='state1' class='clickable'>click to set state2 (title = 'second')</div>
<div id='state2' class='clickable'>click to set state3 (title = 'third')</div>
<br/>
<div id='undo' class='clickable'>undo</div>
有关实时示例,请参见:记录-受Matt答案的启发,我编写了一小段代码,可以自动反转CSS更改:
+1非常好的答案-我觉得我错过了这么简单的解决方案。事实上,我最关心的是在AJAX请求失败后撤消DOM更改,因此没有服务器端更改可恢复。我还没有完全了解这些内容,但这似乎是我问题的解决方案,所以我现在接受你的答案。谢谢@Tomasz,关于上面的代码你有什么特别的问题吗?不,我粗略地理解它,但是我正处于学习JavaScript内部工作的中间,所以当我看到诸如“代码> {} /代码>之类的东西时,我不认为“哦,它只是一个对象!”但是我更喜欢在阴影中看到发生了什么。这会分散我对顶级内容的注意力:-)
// A function that should be called when state changes
var updateTitle = function(opts){
// Update the pages title based on state
console.log('title updating');
$('#title').text(opts.title);
};
var myState = new StateHelper();
myState.onChange(updateTitle); // hook the state change event
// some example states
var state2 = { title: 'second' };
var state3 = { title: 'third' };
// Just some click handlers
$(document).ready(function(){
$('#state1').click(function(){
myState.set(state2);
});
$('#state2').click(function(){
myState.set(state3);
});
$('#undo').click(function(){
myState.undo();
});
// Set initial state
myState.set({title: 'some title'});
});