Javascript 对隐藏值调用jQuery.trigger(';change';)会打破依赖于敲除的可观察值

Javascript 对隐藏值调用jQuery.trigger(';change';)会打破依赖于敲除的可观察值,javascript,jquery,knockout.js,Javascript,Jquery,Knockout.js,在我们遇到这件事的背后有一个故事。。。基本上,我们在所有表单输入上调用trigger('change'),让其他敲除观测值知道它们的值已经重置。但我真的认为这是淘汰赛中的一个错误。在这里询问是否有其他人遇到过它(StackOverflow是一个比Knockout的谷歌论坛更好的界面) 因此,如果您有一个隐藏的输入,其值是绑定到计算的可观察数据的数据,并且您在其上调用jQuery的触发器('change'),它会清除可观察数据。如果深入研究代码,可以看到在视图模型对象上,成员对象被替换为触发更改事

在我们遇到这件事的背后有一个故事。。。基本上,我们在所有表单输入上调用
trigger('change')
,让其他敲除观测值知道它们的值已经重置。但我真的认为这是淘汰赛中的一个错误。在这里询问是否有其他人遇到过它(StackOverflow是一个比Knockout的谷歌论坛更好的界面)

因此,如果您有一个隐藏的输入,其值是绑定到计算的可观察数据的数据,并且您在其上调用jQuery的
触发器('change')
,它会清除可观察数据。如果深入研究代码,可以看到在视图模型对象上,成员对象被替换为触发更改事件之前计算的可观察对象上最后一个值的字符串

JS小提琴,显示动作中的断裂:

它使用console.log输出对象,因此如果您尝试不使用console(IE)的浏览器,请注意。您可以看到依赖的可观察对象工作正常,直到您点击“Break It”按钮,之后,该值停止更新,随后按下输出相同的内容。如果你用触发器('change')注释掉这一行并重新运行小提琴,你可以看到它在每次按下按钮后都会继续工作

抱歉没有问一个真正的问题-我们已经找到了一个解决办法,我们只对未隐藏的输入调用触发器(“更改”)(非常简单的jquery选择器,以防有人好奇):


但我想要一个结论:击倒虫子?还是我做错了?

您不应该将一个正常的计算可观测值绑定到一个读/写绑定,比如
。这会导致它在模型中被覆盖

如果你必须的话,你可以用一个。在这种情况下,您甚至可以使用空白写入功能:

但实际的答案是,您确实不需要在字段上触发
change
事件。处理此问题的更好方法是从视图模型执行此操作。在任何
observable
computed observable
上,您可以调用
valuehassmutated()
函数再次通知所有订阅者最新的值


myObservable.valueHasMutated()

我知道
valueHasMutated()
函数,但我们明确跳过了它。实际上,我们在同一页上有多个viewmodels。整个向导viewmodel执行更改和触发器,并在步骤之间导航。其他ViewModel用于特定控件(如相关选择器格式化日期)。这两者需要完全独立,以便我们可以重用向导viewmodel
trigger('change')
是通知所有其他javascript代码表单已更改的最直接的方法-一些表单在步骤之间被重复使用。现在您已经提到了,我确实记得读过关于不将计算值绑定到读/写变量的内容:-(但是,我们没有选择-序列化必须是不可知的,原因与视图模型相同,因此它必须从具有标准值类型的命名输入中提取。我将研究实现一个可写的计算可观察对象,这样我们在未来的版本中就不会自食其果了。非常感谢您的提示。结论:doin'错了!
$("#"+this.id+" form").each(function() {
    $(this).validate().resetForm();
    this.reset();

    // Do some actions on all the inputs, then filter before calling the trigger
    $(this).find('input,select').data('valid','true').filter(':not(:hidden)').trigger('change');
    $(this).find('label,legend').removeClass('validated-error');
});