2

我正在用 xstate 库编写状态图。

状态图代表一个中等复杂的 UI。

我有几个平行状态,但对于这个问题,我们只考虑两个:

SelectionStatus, 表示选择项,区分子状态SelectedNone, SelectedOne, SelectedMany.

Operation,表示当前正在进行的操作。它有一个名为Idle(当然还有其他一些)的子状态。

有一些事件会触发循环回到Idle子状态的动作,而不是去另一个状态。让我们将它们视为即时操作,例如removeSelected仅删除所选项目的操作(这就是问题的重点)。

removeSelected如果选择仅限于单个项目(实际上是树中的一个节点)或多个(树的一个分支),我将向事件添加条件以执行不同的操作。

用于描述事件的动作和条件的 xstate 语法将是:

removeSelected: {
    Idle: {
         cond: isSelectedOneGuard,
         actions: ['removeOne']
    },
    Idle: {
         cond: isSelectedManyGuard,
         actions: ['removeMany']
    }
}

问题是我Idle在同一对象嵌套级别编写了两个键,这是无效的。

我已经考虑重组状态图以将两个操作分支作为选择分支的子状态,但这似乎比问题更糟糕。

我也考虑过使用像RemovingOneand这样的中间虚拟状态,RemovingMany它只会触发返回到 的转换Idle,但我对它不太满意。

我可以通过删除保护条件来解决这个问题,在通用removeOneOrMany动作处理程序中进行测试,但是我会丢失状态图中不同处理的信息。

有人有类似的问题,可以提供一些建议吗?

(注:这里指的是当前版本的xstate,也就是3.1.1,3.2差不多了,不知道能不能更容易处理这种情况)

谢谢!

4

1 回答 1

6

使用当前语法 (3.1),您可以将不同的“候选转换”放在一个数组中:

removeSelected: [
  {
    target: 'Idle',
    cond: isSelectedOneGuard,
    actions: ['removeOne']
  },
  {
    target: 'Idle',
    cond: isSelectedManyGuard,
    actions: ['removeMany']
  }
]
于 2018-04-11T16:28:03.897 回答