Askaga
Askaga

Reputation: 6331

How are events who lead to UI changes handled/modelled with functional reactive programming?

I've looked into functional reactive programming, but coming from an imperative world i fail to understand how a functional language might react to a user event and adapt its data and UI to reflect the necessary changes.

I've taken a quick look at examples from the Elm homepage, but as far as i understand it essentially allows you to describe (changing) output as function of (changing) input (i.e. "draw a rectangle at the mouse position" which is automatically updated and redrawn).

However, what about single events which usually trigger some action? As an example take any usual app which allows you to edit a document in a window. That window also has a "new" button (or menu item) which opens another window instance. How would that work? I would appreciate if someone could explain the concept behind it.

Upvotes: 1

Views: 1137

Answers (2)

atravers
atravers

Reputation: 505

A more recent implementation of FRP staying close to Conal Elliott and Paul Hudak's original Fran has been developed by Atze van der Ploeg and Koen Classen - it's named FRPNow and the paper along with the (circa 2015) Haskell sources are publicly available as well as a library.

I suggest reading the paper first to get an overview of the implementation before looking at the sources; they differ quite markedly from what's presented in the paper. You can then use the library for actual work and experimentation :-)

As for the original question:

How are events who lead to UI changes handled/modelled with functional reactive programming?

...borrowing from page 3 of the FRPNow paper:

(a) Functions taken from Fran
type E a ≗ (Time+, a) events, where Time+ = Time ∪ {∞}
instance Monad E where
  return x ≗ (-∞, x)
  (ta, a) >>= flet (tb, x) ≗ f a in (max ta tb, x)
how new events can be built using existing ones

(...why "≗" instead of just "="? See page 2 :-)

Upvotes: 0

lukstafi
lukstafi

Reputation: 1895

The short answer is: FRP is inherently not purely functional, as in general reactions to actual external environment are imperative in character. Below I describe a "pure" approach to FRP, there are also more efficient but more "imperative" approaches based on continuations.

• FRP is an attempt to declaratively deal with time.

• Behaviors are functions of time.

◦ A behavior has a specific value in each instant.

• Events are sets of (time, value) pairs.

◦ I.e. they are organised into streams of actions.

• Two problems

◦ Behaviors / events are well defined when they don’t depend on future

◦ Efficiency: minimize overhead

• FRP is synchronous: it is possible to set up for events to happen at the same time, and it is continuous: behaviors can have details at arbitrary time resolution.

◦ Although the results are sampled, there’s no fixed (minimal) time step for specifying behavior.

◦ Asynchrony refers to various ideas so ask what people mean.

• Forcing a lazy list (stream) of events would wait till an event arrives.

• Scanning through an event list since the beginning of time till current time, each time we evaluate a behavior – very wasteful wrt. time&space. Producing a stream of behaviors for the stream of time allows to forget about events already in the past.

• Next optimization is to pair user actions with sampling times. Action Nothing corresponds to sampling time when nothing happens.

• Turning behaviors and events from functions of time into input-output streams is similar to optimizing interesction of ordered lists from O(m n) to O(m + n) time.

• Now we can in turn define events in terms of (optional, Maybe) behaviors, happening at points in time rather than varying over intervals of time.

• This all looks very much like stream processing.

I discuss FRP in a lecture on zippers, adaptive programming, FRP and GUIs but it is OCaml-centric.

Upvotes: 1

Related Questions