Code Monkey home page Code Monkey logo

Comments (7)

ryaninvents avatar ryaninvents commented on August 23, 2024

The following feels like it should work, but I get ERROR: push! called when another signal is still updating. I'm not sure if this is an implementation issue or a conceptual issue; I'll dig deeper tonight when I have more time.

julia> using Reactive

julia> shader = Input(Input("first shader"))
"first shader"

julia> dummyInput = foldl(Input("initial value"), shader) do main, newSignal
           lift((val) -> push!(main, val), newSignal)
       end
"initial value"

julia> lift(dummyInput) do v
           println(string("Value! ", v.value))
       end
Value! initial value
nothing

julia> mySignal = Input("bar")
"bar"

julia> push!(shader, mySignal)
ERROR: push! called when another signal is still updating.
 in push! at /Users/mullery1/.julia/v0.3/Reactive/src/Reactive.jl:257

A similar (but much more complicated) library for JavaScript called Bacon.js has a Bus class which, along with flatMap, would completely get the job done. I think Reactive.jl would benefit greatly from a flatten() function or similar, so you could simply write:

using Reactive
shader = Input(Input("first shader"))
dummyInput = flatten(shader)
lift(shader) do value
  println(string("Got a value: ", value))
end
# now prints "Got a value: first shader"
myNewSignal = Input("second shader")
push!(shader, myNewSignal) # prints "Got a value: second shader"
push!(myNewSignal, "third shader") # prints "Got a value: third shader"

A large part of the power of reactive programming is that you can have signals of signals (or streams of streams, or however you want to think about them). I'd love to see flatten() be added to Reactive.jl.

The only issue that I could see is that whenever you plug in a new signal, it will "hijack" the shader stream. For instance, say you had an initial shader stored in the sourcecode variable in your above example, and then your widget initialized. When the widget plugged its stream into shader its (probably useless) initial value would override the value of sourcecode. You could probably fix this with some kind of dummy initial value that gets dropped, but that feels a bit hacky.

from reactive.jl.

SimonDanisch avatar SimonDanisch commented on August 23, 2024

ERROR: push! called when another signal is still updating
That's supposed to happen, as it's simply not allowed to push inside lifts. You can get around it by sleeping for a while, but it's extremely hacky as it just works in 80% of the time.

Yeah initial values are a bit cumbersome, especially when you work with events, that not yet exist.
I sometimes use an array, which is either empty or holds the value ;) (has quite some overhead though, when I think about it... Better would be the Option type, which I saw flying around somewhere)

push!(signala, signalb) seems to be a lot better than connect! =)

from reactive.jl.

shashi avatar shashi commented on August 23, 2024

@SimonDanisch I think what you are looking for is to merge two signals? merge(::Signal...,) gives a signal which updates when any of the inputs updates.

I still think the right way to do this is not have Reactive as a dependency at all in GLPlot. Maybe only for setting up input signals from the window.

makeshader should just be the do block that is inside.

function useshader( sourcecode)
      #... Make new shader
      #... Delete old shader
      # also tell OpenGL to use the new shader
   end

And then the user could do:

using Reactive
newsource = lift(useshader, lift(x -> readall(open("filename")), every(1.0)))

if they want to update the shaders at all. If they don't want to, they need not even bother learning about Reactive. As for the plot object:

[
:attributename => Input(someValue)
:attributname => SomeLift
....
]

Should definitely be

[ :attributename => someValue, :attributname => someValue2]

And then all you need to take care of is rendering a signal of plots if at all that's what the user wants to render. They can use the input signals from the window to create a signal of plots to render.

What Reactive implements is loosely first order FRP almost identical to Elm. This means the graph can only grow by adding child nodes but cannot change in connectivity. This recent talk explains the tradeoffs when using signals of signals or reconfigurable signal graphs. I quite like the convenience Reactive provides right now without being too complicated.

@baconscript Thanks for the examples. flatten seems like a nice way to allow someone to attach or detach signals. But merge usually gets the job done in the case of one-off interactive UIs such as those in Interact and GLPlot. I'll look into what problems we might face if we introduce flatten. There is also the chance that we could implement Automaton instead as Evan describes it in the talk.

from reactive.jl.

SimonDanisch avatar SimonDanisch commented on August 23, 2024

I need to think about the others, but one quick comment:
one-off interactive UIs such as those in Interact and GLPlot
That's probably exactly where I don't agree... I simply want something more flexible than one off UIs.
I want to have an API, that prepares you a subgraph, which is already set-up to solve a certain sub-problem, but the user can decide how and when to integrate it in the bigger picture.
I think, again, about the other suggestion.

from reactive.jl.

SimonDanisch avatar SimonDanisch commented on August 23, 2024

After watching the video I think it is quite clear:
It's not weather we want this feature, but who will implement it and when...
Automatons, if I understand them correctly, might be what I need, to make things work as intended.

Why do I still use the dicts of Signals?!
It's the simplest way for me, right now, and offers me to switch out signals dynamically, already. So this is my work around at the moment. It doesn't hurt much, as I'm not at a point yet, where I really render in a reactive way.
To get my whole render pipeline working in the real sense of Reactive Programming is on my list. But it will mean huge amounts of work for me, as it's not very easy to elegantly work together with OpenGL, while keeping performance and a straight forward API.
It basically means, to build a reactive 3D scene graph, which will be very challenging.

from reactive.jl.

shashi avatar shashi commented on August 23, 2024

@SimonDanisch I just PR'd an implementation of flatten (#32) which turns out works exactly the way @r24y describes :)

However, I am of the opinion that this must be used sparingly for simplicity.

from reactive.jl.

shashi avatar shashi commented on August 23, 2024

Now that we have flatten and even bind! and unbind!. I guess we can close this...

from reactive.jl.

Related Issues (20)

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.