Elm 为一个模型组合多个信号(使用Html.Events和键盘信号)

Elm 为一个模型组合多个信号(使用Html.Events和键盘信号),elm,Elm,我刚到榆树。我目前在实验中发现了这种语言。尽管信号的使用看起来很复杂。下面是我的网页的一个工作示例,它处理多个段落(添加、删除、编辑等) ——开始 main:signalhtml.Html main=Signal.map(view actions.address)模型 查看:(Signal.Address操作)->Model->Html 查看地址模型=。。。(使用按钮等显示段落) 此代码段启动模型。通过使用Signal.map将动作映射到模型,我能够处理来自按钮的点击事件(导入的Html+事件

我刚到榆树。我目前在实验中发现了这种语言。尽管信号的使用看起来很复杂。下面是我的网页的一个工作示例,它处理多个段落(添加、删除、编辑等)

——开始
main:signalhtml.Html
main=Signal.map(view actions.address)模型
查看:(Signal.Address操作)->Model->Html
查看地址模型=。。。(使用按钮等显示段落)
此代码段启动模型。通过使用
Signal.map
将动作映射到模型,我能够处理来自按钮的点击事件(导入的Html+事件模块)

模型:信号模型
model=Signal.foldp update makeEmptyModel actions.Signal
在这里,我从一个空模型开始。
update
功能允许我在单击按钮上的事件后更新模型

更新:操作->模型->模型
更新操作模型=。。。。
操作
是一种处理我定义的多个操作的类型,如“addParague”、“removeParague”

到目前为止,这是可行的。现在,在检查包裹时,我发现。这看起来很有趣,所以我想添加一个新功能。如果用户按Alt+A,则所有段落都被选中。(如文件资源管理器中的Ctrl+A)

但是,要将它与我现有的当前信号映射结合起来似乎并不容易。我决定深入研究并找到了答案。这样我就可以用对了?我试图将键盘信号合并到当前信号的尝试失败

main=Signal.merge
(Signal.map(view actions.address)模型)
(Signal.map(view actions.address)键向下)
(向下键来自导入键盘(向下键)import)

但这不起作用。我得到下一个错误

The 2nd argument to function `map` is causing a mismatch.
160│      Signal.map (view actions.address) keysDown)
                                            ^^^^^^^^
Function `map` is expecting the 2nd argument to be:
Signal { focused : Bool, selected : Bool, ... }

But it is:
    Signal (Set.Set Char.KeyCode)
似乎在使用
Signal.merge
时,它需要处理相同输出的多个信号。这就是我想要的。但这似乎不起作用

问题:如何在当前设计中添加键盘信号?

还是我对
信号.合并的期望有误?我正在使用
信号。合并
用于错误目的?我应该改用吗?如果是,我如何将其用于当前示例*?还是有更好的方法

  • 如果解决方案是map2,您可以添加解释吗?那是因为我不懂“地图2”的东西

发送到
合并的信号必须是相同类型的。在合并之前,您需要添加另一个将键盘输入映射到
操作的函数

有几种方法可以实现这一点。下面是一个使用基本计数器示例和
Signal.merge
的示例。重要的是使用
keyPressesToAction
信号映射功能

导入信号
导入Html公开(…)
导入Html.Events公开(..)
输入键盘
导入字符
类型动作=NoOp |增量|减量
操作:信号。邮箱操作
行动=
信号信箱NoOp
更新动作模型=
案例诉讼
NoOp->model
增量->模型+1
减量->型号-1
模型=
Signal.foldp更新0(Signal.merge actions.Signal key pressestoaction)
按键停止动作=
让
按键代码动作按键代码=
case Char.fromCode keyCode of
“+”->增量
'-'->减量
_->NoOp
在里面
Signal.map keycode到Action Keyboard.press
主要=
Signal.map(view actions.address)模型
视图地址模型=
分区[]
[按钮[点击地址递减][文本“-”]

,text发送到
合并
的信号必须是同一类型。合并之前,您需要添加另一个将键盘输入映射到
操作
的功能

有几种方法可以实现这一点。下面是一个使用基本计数器示例和
Signal.merge
的示例。重要的是使用
keyPressesToAction
信号映射功能

导入信号
导入Html公开(…)
导入Html.Events公开(..)
输入键盘
导入字符
类型动作=NoOp |增量|减量
操作:信号。邮箱操作
行动=
信号信箱NoOp
更新动作模型=
案例诉讼
NoOp->model
增量->模型+1
减量->型号-1
模型=
Signal.foldp更新0(Signal.merge actions.Signal key pressestoaction)
按键停止动作=
让
按键代码动作按键代码=
case Char.fromCode keyCode of
“+”->增量
'-'->减量
_->NoOp
在里面
Signal.map keycode到Action Keyboard.press
主要=
Signal.map(view actions.address)模型
视图地址模型=
分区[]
[按钮[点击地址递减][文本“-”]

,文本,因此,我使用了
信号。错误地合并了
。但是,现在我无法添加段落。我有一个可以插入文本的文本区域。当我单击按钮时,它会将该文本添加到我创建的段落中。即使使用您的端口解决方案,我甚至无法将文本数据输入到我的文本区域。这是因为
->NoOp
of Keypress EstoAction会覆盖它。我如何确保只有按Alt键才能发送信号?然后我可以使用Alt+A Simply这很难在没有看到您的代码的情况下进行诊断。听起来可能是其他原因造成的。处理按键信号不应影响文本框的键入。我已经对您的示例(第一个代码块)进行了c/p'ed在和上,使用“+”和“-”键不起作用。但单击这些按钮可以起作用。可能有些地方不正确:)看起来有一个有待解决的问题,应该很快解决。该示例在Chrome中运行良好。也许您的代码也可以在Chrome中运行?因此,我错误地使用了
Signal.merge
,但是,现在我无法添加段落。我有一个文本区,我可以在其中插入文本。当我点击按钮时,它会添加