Data binding 验证错误阻止撤消

Data binding 验证错误阻止撤消,data-binding,eclipse-emf,emf,eclipse-databinding,Data Binding,Eclipse Emf,Emf,Eclipse Databinding,我的基于EMF的Eclipse应用程序存在以下问题: 撤销很好。验证工作正常。但是当GUI字段中的数据出现验证错误时,这会阻止撤消操作的使用。例如,无法撤消以返回该字段的有效状态 在此图片中,无法使用撤消: 应用程序中使用的工具: Eclipse数据绑定 UpdateValueStrategys对绑定进行验证 撤消是使用标准的UndoAction实现的,该操作调用CommandStack.Undo 将验证框架连接到基于Eclipse表单的GUI的MessageManagerSupport类

我的基于EMF的Eclipse应用程序存在以下问题:

撤销很好。验证工作正常。但是当GUI字段中的数据出现验证错误时,这会阻止撤消操作的使用。例如,无法撤消以返回该字段的有效状态

在此图片中,无法使用撤消:


应用程序中使用的工具:

  • Eclipse数据绑定
  • UpdateValueStrategy
    s对绑定进行验证
  • 撤消是使用标准的
    UndoAction
    实现的,该操作调用
    CommandStack.Undo
  • 将验证框架连接到基于Eclipse表单的GUI的
    MessageManagerSupport
数据绑定如下所示:

dataBindingContext.bindValue(WidgetProperties.text(…),
值(…),validatingUpdateStrategy,null);

问题是:

  • “撤消”系统对更改模型的命令起作用
  • 当存在验证错误时,验证系统会阻止更新到达模型
要在出现验证错误时使撤销生效,我想我可以做以下不同的事情之一:

  • 使撤消系统在GUI层上工作。(这将是一个巨大的变化,可能根本不可能使用EMF来实现这一点。)
  • 以与有效数据相同的方式,在GUI触发器命令中生成更改模型数据的无效数据。(只要数据不能保存到磁盘,这就可以了。但我找不到一种方法。)
  • 使验证直接在模型上工作,可能由
    资源
    上的内容侦听器触发。(这是验证策略的一大变化。在这个阶段,似乎不可能跟踪源GUI控件。)
  • 这些解决方案要么看起来不可能,要么有严重的缺点

    即使存在验证错误,使撤消也能工作的最佳方法是什么


    注意:我接受Mad Matts的回答,因为他们的建议引导我找到了解决方案。但我并不十分满意,我希望有一个更好的


    如果某个人在某个时候找到了更好的解决方案,我会很乐意接受它而不是现在的。strong>

    验证程序可以保护目标值不受无效值的影响。 因此,在出现无效值的情况下,目标命令堆栈保持不变。 为什么要强制设置无效值?GUI中的
    ctrl+z
    是否足以重置上一个有效状态

    如果仍要将这些值设置为实际的目标模型,可以使用
    updateValue策略

    更新阶段包括:

  • 获取后验证-获取后验证(对象)

  • 转换-转换(对象)

  • 转换后验证-validateAfterConvert(对象)

  • 设置前验证-验证前验证集(对象)

  • 值集-doSet(IObservableValue,对象)

  • 我不确定验证错误(
    Status.error
    )确切发生在哪里,但您可以检查发生在哪里,然后手动强制执行
    SetCommand

    您可以将每个步骤的自定义
    IValidator
    设置为您的
    UpdateValueStrategy

    验证程序保护您的目标值不受无效值的影响是有意义的。 因此,在出现无效值的情况下,目标命令堆栈保持不变。 为什么要强制设置无效值?GUI中的
    ctrl+z
    是否足以重置上一个有效状态

    如果仍要将这些值设置为实际的目标模型,可以使用
    updateValue策略

    更新阶段包括:

  • 获取后验证-获取后验证(对象)

  • 转换-转换(对象)

  • 转换后验证-validateAfterConvert(对象)

  • 设置前验证-验证前验证集(对象)

  • 值集-doSet(IObservableValue,对象)

  • 我不确定验证错误(
    Status.error
    )确切发生在哪里,但您可以检查发生在哪里,然后手动强制执行
    SetCommand

    您可以将每个步骤的自定义
    IValidator
    设置为您的
    UpdateValueStrategy

    注意:这是我在应用程序中使用的解决方案。我对它不是很满意。我认为这有点像黑客

    我接受Mad Matts的回答,因为他们的建议引导我找到了这个解决方案

    如果某个人在某个时候找到了更好的解决方案,我会很乐意接受它而不是现在的。强>


    我最终创建了一个
    UpdateValueStratety
    子类,它在模型对象上设置了一个值之后运行一个验证器。这似乎很有效

    我创建这个答案是为了发布我最终使用的代码。这是:

    /**
    *可以在设置值后执行验证的{@link UpdateValueStrategy}
    *在模型中。之所以使用此选项,是因为如果未在中更改模型,“撤消”将不起作用。
    */
    公共类LateValidationUpdateValueStrategy扩展了UpdateValueStrategy{
    专用IValidator验证器;
    公共无效setAfterSetValidator(IValidator afterSetValidator){
    this.afterSetValidator=afterSetValidator;
    }
    @凌驾
    受保护的IStatus doSet(IObservableValue observableValue,对象值){
    IStatus setStatus=super.doSet(可观测值,值);
    if(setStatus.getSeverity()>=IStatus.ERROR | | afterSetValidator==null){
    返回状态;
    }
    //我在这里使用了一个验证器,它调用EMF生成的模型验证器。
    //在tha中