如果按下发生在游戏窗口里,释放却发生在其他窗口,游戏可能没有收到原来的释放事件。因此焦点改变本身也应能重置按住状态。
先固定规则与数据
模型初始有焦点且没有按键按住。失去焦点立即清空按键;无焦点时忽略按键事件;恢复焦点不会自动恢复旧按键。重复的按下只保持状态,不再次生成首次按下边沿。
初始窗口有焦点、按键集合为空;down按下、up释放、blur失焦、focus恢复焦点。
逐项记录过程
事件1['down', 'A'],焦点True,按住集合['A'],本次新增按下边沿['A']。
事件2['down', 'A'],焦点True,按住集合['A'],本次新增按下边沿[]。
事件3['blur'],焦点False,按住集合[],本次新增按下边沿[]。
事件4['up', 'A'],焦点False,按住集合[],本次新增按下边沿[]。
事件5['focus'],焦点True,按住集合[],本次新增按下边沿[]。
事件6['down', 'A'],焦点True,按住集合['A'],本次新增按下边沿['A']。
事件7['up', 'C'],焦点True,按住集合['A'],本次新增按下边沿[]。
事件8['up', 'D'],焦点True,按住集合['A'],本次新增按下边沿[]。
事件9['down', 'B'],焦点True,按住集合['A', 'B'],本次新增按下边沿['B']。
事件10['down', 'D'],焦点True,按住集合['A', 'B', 'D'],本次新增按下边沿['D']。
事件11['focus'],焦点True,按住集合['A', 'B', 'D'],本次新增按下边沿[]。
事件12['down', 'A'],焦点True,按住集合['A', 'B', 'D'],本次新增按下边沿[]。
事件13['down', 'B'],焦点True,按住集合['A', 'B', 'D'],本次新增按下边沿[]。
事件14['up', 'C'],焦点True,按住集合['A', 'B', 'D'],本次新增按下边沿[]。
事件15['down', 'C'],焦点True,按住集合['A', 'B', 'C', 'D'],本次新增按下边沿['C']。
事件16['blur'],焦点False,按住集合[],本次新增按下边沿[]。
事件17['down', 'B'],焦点False,按住集合[],本次新增按下边沿[]。
事件18['down', 'B'],焦点False,按住集合[],本次新增按下边沿[]。
事件19['up', 'C'],焦点False,按住集合[],本次新增按下边沿[]。
事件20['up', 'C'],焦点False,按住集合[],本次新增按下边沿[]。
事件21['up', 'B'],焦点False,按住集合[],本次新增按下边沿[]。
事件22['down', 'A'],焦点False,按住集合[],本次新增按下边沿[]。
事件23['blur'],焦点False,按住集合[],本次新增按下边沿[]。
事件24['down', 'B'],焦点False,按住集合[],本次新增按下边沿[]。
事件25['blur'],焦点False,按住集合[],本次新增按下边沿[]。
事件26['focus'],焦点True,按住集合[],本次新增按下边沿[]。
末尾再次失焦并恢复后,按住集合应为空。恢复焦点只恢复接收能力,不恢复以前的按住状态。
独立复核的方法
逐事件记录焦点、按住集合和新增边沿,确认失焦后集合为空。恢复焦点后的第一次有效按下才能重新产生边沿,不能依赖之前窗口外是否出现过释放。
建议先按原始数据自己算一遍,保留中间状态后再与本例对照。发生分歧时,先寻找最早不同的步骤,检查边界是否包含、编号与坐标方向是否一致,以及状态是在事件之前还是之后更新。最终结果相同并不能替代对过程规则的理解,修改输入后也需要重新核算。
使用范围
这是一个明确的输入管理模型,不是在描述所有操作系统如何发送事件。实际引擎还可能需要取消拖动、蓄力和鼠标捕获;这些行为应按游戏规则另外处理。
