Day24 - 在 XState 中的阶层式状态 Hierarchical States

还记得我们在 Day 14 的例子吗?

https://ithelp.ithome.com.tw/upload/images/20210927/20130721esiomcqiFn.png

https://ithelp.ithome.com.tw/upload/images/20210929/20130721UvlbWhoZpj.png

这是一个比较符合现实情境的 Input 元件状态,只有当 input content 有改变时, valid / invalid 的情境才是有意义的。也就是说 changed 这个父阶层底下会有 valid / invalid 的两种「状态」及改变状态的「事件」。

1. 如何在 XState 描述 Hierarchical States

以下是 2 个 一般的 FSM

  // door machine config
  const doorMachinceConfig = {
    id: "door",
    initial: "关着",
    states: {
      关着: {
        on: { 开门: "开了" }
      },
      开了: {
        on: {
          关门: { target: "关着" }
        }
      }
    }
  };
  
 // some FSM config
 const someFSMConfig = {
    id: "myId",
    initial: "state1",
    states: {
      state1: {
        on: {
          event1: { target: "state2" }
        }
      },
      state2: {
        on: {
          event2: { target: "state1" }
        }
      }
    }
  };
  

我们说阶层状态,也就是某个状态底下有子状态、子状态机的意思!
那就是把某个状态机的定义丢进另一个状态机之下的「特定状态後」,就可以完成了!

比方说,someFSMConfigstate2 是个阶层状态,底下是一个 doorMachine,那...

  // door machine config
  const doorMachinceConfig = {
    id: "door",
    initial: "关着",
    states: {
      关着: {
        on: { 开门: "开了" }
      },
      开了: {
        on: {
          关门: { target: "关着" }
        }
      }
    }
  };
  
 // some FSM config
 const someFSMConfig = {
    id: "myId",
    initial: "state1",
    states: {
      state1: {
        on: {
          event1: { target: "state2" }
        }
      },
      state2: {
        on: {
          event2: { target: "state1" }
-       }
+       },
+       ...doorMachinceConfig,
      }
    }
  };
  

只要把这个子状态机的定义丢进父状态底下即可!
https://ithelp.ithome.com.tw/upload/images/20211009/20130721o35TXe1xOx.png

范例可参考Example Demo


2. 完成需求

const inputMachine = Machine({
  id: "inputMachine_v2",
  type: "parallel",

  states: {
    enabled: {
      initial: "enabled",
      states: {
        disabled: {
          on: {
            ENABLE: { target: "enabled" },
          },
        },
        enabled: {
          on: {
            DISABLE: { target: "disabled" },
          },
        },
      },
    },
    changed: {
      initial: "unchanged",
      states: {
        unchanged: {
          on: {
            CHANGE: { target: "changed" },
          },
        },
        changed: {
          initial: "valid",
          states: {
            invalid: {
              on: {
                VALIDATE: { target: "valid" },
              },
            },
            valid: {
              on: {
                INVALIDATE: { target: "invalid" },
              },
            },
          },
        },
      },
    },
  },
});

DEMO Visualizer

https://ithelp.ithome.com.tw/upload/images/20211009/20130721n0YAXCb28a.png

这两天的描述都比较仓促、比较短,如果有哪里有疑问或是建议补充的,也欢迎大家指教一下!

参考资料

https://xstate.js.org/docs/guides/hierarchical.html


<<:  [Day 28] 第二主餐 pt.4-程序不求人,runserver背景执行及crontab自动执行

>>:  Day39 ( 游戏设计 ) 青蛙过河

哪些行当应该涨工资?你的行业有机会涨吗?

物价飞涨,你的工资已经多久没涨了?工资涨幅跟得上物价的涨幅吗?生活压力太大,所有人都盼望可以涨工资。...

[Day 06] 一个单元测试的题目-闰年的判断

过了这麽多天, 我们终於进入到主题了, 这一次我们使用的题目, 是输入一个正整数(西元年), 然後判...

Day 19:AWS 是什麽?30天从动漫/影视作品看AWS服务应用 -《尼尔:自动人形》

今年春天重版出来的《尼尔:人工生命 ver.1.22474487139...》第二代《尼尔:自动人形...

企划实现(21)

接续上篇继续提到关於有限公司以及股份有限公司的差别。 有限公司以及股份有限公司除了制度会有差别外,责...

第45篇-lsmod命令

进度 : 鸟哥的 Linux 私房菜 -- 第十九章、开机流程、模组管理与 Loader 的 lsm...