Giter Club home page Giter Club logo

interactbase.jl's People

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar

interactbase.jl's Issues

API consistency review

This is an issue to decide the InteractBase API. The current approach tries to be as compatible as possible with the Interact.jl API which in turn is not fully consistent.

In Interact.jl, almost all arguments can be used as keyword arguments and a "positional" version is provided, that can take as positional version the most "commonly used" keyword argument. It generally is value, but sometimes is placeholder and other times it's label. Still, there is some logic: the positional argument is placeholder for text input, value for "type input" (meaning input of non text types, like Bool, Date, Color,..) and label for buttons. Here is the current API reference.

One alternative would be as follows:

  • positional arguments are: arguments that define what values are allowed (meaning either options or range for a slider) and value
  • everything else is a keyword argument, following the HTML5 name (placeholder, label, multiple, etc...)

The "fly in the ointment" of this rewrite is button as the HTML5 version of button takes argument that are not "keyword" and are the content of the button (generally label and icon). In this case I see as sensible both signatures:

  • button(args...; value=0, kwargs...) where args would be the button content (icon and label)
  • button(value = 0, label = "press me", icon = nothing, kwargs....)

What is the consensus? Is it preferred to:

  1. Keep as is
  2. Go for the new design

And, in case of 2), what should the signature of button be?

cc: @shashi, @JobJob

Cannot use backspace or arrow keys in textbox.

When trying out textbox (using the Bulma backend) in Juno, I found that some normal keyboard input is ignored. I cannot use backspace, nor can I use the arrow keys to navigate in the text. I can however drag and drop parts of the text, indicating that it is possible to edit it.

using WebIO
using InteractBulma

textbox()

This is not important to me, I just thought that I'd raise the issue.

@eval code generation is kind of confusing!

I was trying to track some broken styling in inputs.jl, but the eval blocks make it a little hard to track what is happening! I'm wondering if it is worth having them at all, in terms of the obfuscation vs DRYness ratio they deliver.

You could get a lot off the way by just extracting a few shared functions, say in slider.jl:

slider(WT::WidgetTheme, vals::AbstractArray, formatted_vals = format.(vec(vals)); value = medianelement(vals), kwargs...) =
    build_slider(slider, WT, vals, formatted_vals, value)

rangeslider(WT::WidgetTheme, vals::AbstractArray, formatted_vals = format.(vec(vals)); value = medianelement(vals), kwargs...) =
    build_slider(rangeslider, WT, vals, formatted_vals, value)

function build_slider(f, WT, vals, formatted_vals, value)
    T = Observables._val(value) isa Vector ? Vector{eltype(vals)} : eltype(vals)
    value isa AbstractObservable || (value = Observable{T}(value))
    vals = vec(vals)
    indices = axes(vals)[1]
    f = x -> _map(t -> searchsortedfirst(vals, t), x)
    g = x -> vals[Int.(x)]
    ObservablePair(value, f = f, g = g).second

    value = build_value(vals, value)
    index = build_index(vals)

    wdg = Widget(f(WT, indices, formatted_vals; value = index, kwargs...), output = value)
    wdg["value"] = value
    wdg
end

Anyway, that is just my 2 cents! And mostly because I imagine I'll be reading this code a lot more, because its so useful :)

Widget for displaying text

I was thinking that a widget that can display some sort of message could be very useful in GUIs programming. In this sense it would be a text area that doesn't take input but only shows a string.

TagBot trigger issue

This issue is used to trigger TagBot; feel free to unsubscribe.

If you haven't already, you should update your TagBot.yml to include issue comment triggers.
Please see this post on Discourse for instructions and more details.

If you'd like for me to do this for you, comment TagBot fix on this issue.
I'll open a PR within a few hours, please be patient!

Allow observables in more places

All widget arguments that are passed to Knockout (e.g. the list of options) should also accept Observables and when upgraded Knockout would automatically update only that part of the widget.

Filepicker widget doesn't respond when selecting the same file

When I use the filepicker widget, I would like to get a response for a callback function even when I select the same same twice or more times. The current behavior just ignores the callback for the same file selection.

This is a minimal working example:

using Blink, Interact
w = Window();
picker = filepicker();
on((n) -> println(picker[]), picker);
body!(w, picker);

, after that, it is necessary to select the same file multiple times and check that the println() function is only called once.

Here is an screeshoot that shows the behavior more clearly:
image

I'm using the latests versions of Interact and InteractBase, 0.10.5 and 0.10.10 respectively.

Maybe, the filepicker widget was meant to behave like that, however I need to detect selections even though the same file is chosen. Any ideas to overcome this?

Dialog fails since theme is undefined

Describe the bug
Theme is undefined on this line in dialog
https://github.com/piever/InteractBase.jl/blob/0a91fe6d605cafcb27b1b9c15d5fea568fb187da/src/input.jl#L113

Original report here:
JuliaGizmos/Interact.jl#414

To Reproduce
See JuliaGizmos/Interact.jl#414

Expected behavior
theme should be defined.

Screenshots
See JuliaGizmos/Interact.jl#414

Version info (please complete the following information):

  • include the output of versioninfo() and Pkg.status()
  • how are you deploying the widgets? Jupyter Notebook/Lab, Juno, Blink or Mux?

Before opening an issue

  • make sure you are on the latest release of InteractBase and try rebuilding it with Pkg.build("InteractBase")

If widgets do not appear

  • test that your WebIO is correctly installed. Make sure you're on latest release and rebuild it with Pkg.build("WebIO")
  • try a simple code to produce a slider: using WebIO; display(Node(:input, attributes = Dict("type" => "range")))
  • if this doesn't produce a slider, your WebIO is not installed correctly and you may wish to open an issue at WebIO rather than here,

Styling, layout tweaks and how to help out

Now that this is released and I have Flatten.jl I don't need AutoInteract.jl anymore... I'll be directly using this packages for making UIs, so I was wondering how my efforts to polish project layouts could be contributed back where possible.

There are lots of small details like labels overlapping sliders when widgets are smaller that I need to tweak for two projects over the next week. It would be good to do those fixes in a generally useful way, if you have any pointers on that!

I also have some nice formatting helpers from AutoInteract such as column layouts for large groups of widgets, and those could be good to include in the Interact ecosystem somehow.

Issues accessing bootcss.com

I tried installing and running this at work but it fails at the build step with Failed to connect to cdn.bootcss.com port 443: Operation timed out. Upon investigation it turns out this is because bootcss.com is hosted in China and the office firewall blocks connections to Chinese websites.

This surprised me—isn't bootstrap hosted at maxcdn.bootstrapcdn.com? What is bootcss.com and why is it in China?

no output on MacOs

when trying one of the docs examples

using InteractBase, InteractUIkit, WebIO

width, height = 700, 300
colors = ["black", "gray", "silver", "maroon", "red", "olive", "yellow", "green", "lime", "teal", "aqua", "navy", "blue", "purple", "fuchsia"]
color(i) = colors[i%length(colors)+1]
ui = @manipulate for nsamples in 1:200,
        sample_step in slider(0.01:0.01:1.0, value=0.1, label="sample step"),
        phase in slider(0:0.1:2pi, value=0.0, label="phase"),
        radii in 0.1:0.1:60
    cxs_unscaled = [i*sample_step + phase for i in 1:nsamples]
    cys = sin.(cxs_unscaled) .* height/3 .+ height/2
    cxs = cxs_unscaled .* width/4pi
    dom"svg:svg[width=$width, height=$height]"(
        (dom"svg:circle[cx=$(cxs[i]), cy=$(cys[i]), r=$radii, fill=$(color(i))]"()
            for i in 1:nsamples)...
    )
end
display(ui)

the result is that it runs without error, but there is no output. The widget does not materialize.

julia> versioninfo()
Julia Version 0.6.4
Commit 9d11f62bcb (2018-07-09 19:09 UTC)
Platform Info:
  OS: macOS (x86_64-apple-darwin14.5.0)
  CPU: Intel(R) Core(TM) i5-5250U CPU @ 1.60GHz
  WORD_SIZE: 64
  BLAS: libopenblas (USE64BITINT DYNAMIC_ARCH NO_AFFINITY Haswell MAX_THREADS=16)
  LAPACK: libopenblas64_
  LIBM: libopenlibm
  LLVM: libLLVM-3.9.1 (ORCJIT, broadwell)

slider fails with Integer range

Yesterday I stumbled across a stange misbehaviour of sliders with Integer ranges.

slider(5:10) will not evaluate correctly, whereas slider(collect(5:10)) does.
The reason is that the slider method from Widgets, which adds the backend, will directly jump to the slider method, which generates the ui. (Thanks to @tkoolen and @stevengj who helped me understand the issue!)
To prevent this, I propose to add another method

slider(vals::AbstractRange{<:Integer}, args... ; kwargs...) = slider(collect(vals), args... ; kwargs...)

One might add a hint somewhere that calling the backend directly would need a collect for Integer ranges.

Strange behaviours of slider() with arrays of negative numbers

Describe the bug
A clear and concise description of what the bug is.

Sliders do not accept arrays containing negative numbers larger than -21 when a value keyword is used.
I couldn't track down exactly where this is happening.

To Reproduce
Steps to reproduce the behavior.

julia> InteractBase.slider(collect(0.0:-1.0:-25.0), value=-10.0)
ERROR: BoundsError: attempt to access 26-element Array{String,1} at index [27]
Stacktrace:
 [1] ./array.jl:731
 [2] /home/raf/.julia/dev/InteractBase/src/slider.jl:68
 [3] ./none:0
 [4] /home/raf/.julia/dev/InteractBase/src/slider.jl:24
 [5] ./simdloop.jl:0 [inlined]
 [6] ./none:0
 [7] /home/raf/.julia/dev/InteractBase/src/defaults.jl:12
 [8] ./none:0
 [9] none:0

Expected behavior
A clear and concise description of what you expected to happen.

Return a slider! As with InteractBase.slider(collect(0.0:-1.0:-20.0), value=-10.0) or any positive numbers.

Interestingly this works if the first number in the array is larger than some distance from the minimum negative val:

julia>             InteractBase.slider(collect(2.0:-1.0:-24.0), value=-10.0)
ERROR: BoundsError: attempt to access 27-element Array{String,1} at index [28]
Stacktrace:
 [1] getindex(::Array{String,1}, ::Int64) at ./array.jl:731
 [2] #slider#75(::String, ::String, ::Observables.Observable{Any}, ::Base.Iterators.Pairs{Union{},Union{},Tuple{},NamedTuple{(),Tuple{}}}, ::Function, ::NativeHTML, ::Base.OneTo{Int64}, ::Array{String,1}) at /home/raf/.julia/dev/InteractBase/src/slider.jl:68
 [3] (::getfield(InteractBase, Symbol("#kw##slider")))(::NamedTuple{(:value,),Tuple{Observables.Observable{Any}}}, ::typeof(slider), ::NativeHTML, ::Base.OneTo{Int64}, ::Array{String,1}) at ./none:0
 [4] #slider#67(::Float64, ::Base.Iterators.Pairs{Union{},Union{},Tuple{},NamedTuple{(),Tuple{}}}, ::Function, ::NativeHTML, ::Array{Float64,1}, ::Array{String,1}) at /home/raf/.julia/dev/InteractBase/src/slider.jl:24
 [5] #slider at ./simdloop.jl:0 [inlined]
 [6] (::getfield(InteractBase, Symbol("#kw##slider")))(::NamedTuple{(:value,),Tuple{Float64}}, ::typeof(slider), ::NativeHTML, ::Array{Float64,1}) at ./none:0
 [7] #slider#170(::Base.Iterators.Pairs{Symbol,Float64,Tuple{Symbol},NamedTuple{(:value,),Tuple{Float64}}}, ::Function, ::Array{Float64,1}) at /home/raf/.julia/dev/InteractBase/src/defaults.jl:12
 [8] (::getfield(InteractBase, Symbol("#kw##slider")))(::NamedTuple{(:value,),Tuple{Float64}}, ::typeof(slider), ::Array{Float64,1}) at ./none:0
 [9] top-level scope at none:0

But:

julia>             InteractBase.slider(collect(3.0:-1.0:-24.0), value=-10.0)
Widget{:slider,Float64}(OrderedCollections.OrderedDict{Symbol,Any}(:changes=>Observable{Int64} with 1 listeners. Value:
0,:index=>Observable{Any} with 2 listeners. Value:
1,:formatted_vals=>Observable{Any} with 1 listeners. Value:
...

Screenshots
If applicable, add screenshots to help explain your problem.

Version info (please complete the following information):

  • include the output of versioninfo() and Pkg.status()
  • how are you deploying the widgets? Jupyter Notebook/Lab, Juno, Blink or Mux?

Julia Version 1.0.2
Commit d789231e99 (2018-11-08 20:11 UTC)
Platform Info:
OS: Linux (x86_64-pc-linux-gnu)
CPU: Intel(R) Core(TM) i7-8700K CPU @ 3.70GHz
WORD_SIZE: 64
LIBM: libopenlibm
LLVM: libLLVM-6.0.0 (ORCJIT, skylake)
Environment:
JULIA_NUM_THREADS = 5
julia> Pkg.status()
Status ~/.julia/environments/v1.0/Project.toml
[f5f396d3] ApproxBayes v0.3.0
[c9ce4bd3] ArchGDAL v0.2.0
[bf4720bc] AssetRegistry v0.1.0
[6e4b80f9] BenchmarkTools v0.4.2
[ad839575] Blink v0.9.0
[70588ee8] CSSUtil v0.1.0
[159f3aea] Cairo v0.5.6
[a5dba43e] Cellular v0.0.0 [~/julia/Cellular]
[5ae59095] Colors v0.9.5
[a8cc5b0e] Crayons v1.0.0
[a93c6f00] DataFrames v0.17.0
[ab62b9b5] DeepDiffs v1.1.0
[0c46a032] DifferentialEquations v5.3.1
[72d8b834] Dispersal v0.0.0 [~/julia/Dispersal]
[31c24e10] Distributions v0.16.4
[6ffd65d2] DynamicEnergyBudgets v0.0.0 [~/julia/DynamicEnergyBudgets]
[49426c49] FieldDefaults v0.0.1+ [~/julia/FieldDefaults]
[bf96fef3] FieldMetadata v0.0.3+ [~/julia/FieldMetadata]
[4c728ea3] Flatten v0.1.0+ [~/julia/Flatten]
[4c0ca9eb] Gtk v0.16.4
[f67ccb44] HDF5 v0.11.0
[6218d12a] ImageMagick v0.7.1
[916415d5] Images v0.17.0
[c601a237] Interact v0.9.0
[d3863d7c] InteractBase v0.8.2+ [~/.julia/dev/InteractBase]
[7981ab7d] InteractBulma v0.4.2
[033835bb] JLD2 v0.1.2
[2ee39098] LabelledArrays v0.4.0+ [~/.julia/dev/LabelledArrays]
[23fbe1c1] Latexify v0.6.0
[e0eb800d] Microclimate v0.0.0 [~/julia/Microclimate]
[2a8e4939] Mixers v0.1.0+ [~/julia/Mixers]
[a975b10e] Mux v0.5.3
[85f8d34a] NCDatasets v0.6.0
[30363a11] NetCDF v0.7.2
[f7c12bf4] NicheMap v0.0.0 [~/julia/NicheMap]
[510215fc] Observables v0.2.3
[6fe1bfb0] OffsetArrays v0.9.1
[5fb14364] OhMyREPL v0.4.1
[429524aa] Optim v0.17.2
[1dea7af3] OrdinaryDiffEq v4.21.1
[d96e819e] Parameters v0.10.3
[5e10c064] Photosynthesis v0.0.0 [~/julia/Photosynthesis]
[48f930ff] PlotNested v0.0.0 [~/julia/PlotNested]
[91a5bcdd] Plots v0.23.0
[c46f51b8] ProfileView v0.4.0
[061b77f0] REPLGamesBase v0.1.0 #master (https://github.com/ChristianKurz/REPLGamesBase.jl)
[ae029012] Requires v0.5.2
[295af30f] Revise v1.0.2+ [~/.julia/dev/Revise]
[eac7fb6e] ReviseTest v0.0.0 [~/.julia/dev/ReviseTest]
[1bc83da4] SafeTestsets v0.0.1
[6accb78c] SimpleRoots v0.0.0 [~/julia/SimpleRoots]
[90137ffa] StaticArrays v0.10.2
[f3b207a7] StatsPlots v0.10.0
[eb3e9d2b] StructuralInheritance v0.2.4
[a759f4b9] TimerOutputs v0.4.0
[9d95f2ec] TypedTables v1.1.0
[ebadf6b4] UnicodeGraphics v0.0.1+ [~/julia/UnicodeGraphics]
[1986cc42] Unitful v0.14.0+ [~/.julia/dev/Unitful]
[2a06ce6d] UnitfulPlots v0.0.0 [~/julia/UnitfulPlots]
[03de777c] UnitlessFlatten v0.0.1+ [~/julia/UnitlessFlatten]
[0f1e0344] WebIO v0.7.0
[104b5d7c] WebSockets v1.2.0
[cc8bc4a8] Widgets v0.4.4

Before opening an issue

  • make sure you are on the latest release of InteractBase and try rebuilding it with Pkg.build("InteractBase")

If widgets do not appear

  • test that your WebIO is correctly installed. Make sure you're on latest release and rebuild it with Pkg.build("WebIO")
  • try a simple code to produce a slider: using WebIO; display(Node(:input, attributes = Dict("type" => "range")))
  • if this doesn't produce a slider, your WebIO is not installed correctly and you may wish to open an issue at WebIO rather than here,

When rangeslider(;orientation="vertical"), smaller value is upper

When I was trying Vertical Range Slider, I wrote next code.

using Interact, Blink
win = Window();
ui = rangeslider(0:100; value=[30, 80], orientation="vertical");
body!(win, ui)

But, this Range Slider is ... the smaller value is upper, the bigger value is below.
It is not the result I expected.

I found the option Direction at NoUiSlider site.

But, it is not selectable with Widgets.rangeslider().

I suggest that direction option is selectable.

When next change,

diff --git a/src/slider.jl b/src/slider.jl
index dbc44c2..778a476 100644
--- a/src/slider.jl
+++ b/src/slider.jl
@@ -82,13 +82,14 @@ Pass a vector to `value` with two values if you want to select a range.
 """
 function rangeslider(theme::WidgetTheme, vals::AbstractUnitRange{<:Integer}, formatted_vals = format.(vals);
     style = Dict(), label = nothing, value = medianelement(vals), orientation = "horizontal", readout = true,
-    className = "is-primary")
+    className = "is-primary", direction = "ltr")
 
     T = Observables.to_value(value) isa Vector ? Vector{eltype(vals)} : eltype(vals)
     value isa AbstractObservable || (value = Observable{T}(value))
 
     index = value
     orientation = string(orientation)
+    direction = string(direction)
     preprocess = T<:Vector ? js"unencoded.map(Math.round)" : js"Math.round(unencoded[0])"
 
     scp = Scope(imports = vcat([nouislider_min_js, nouislider_min_css], libraries(theme)))
@@ -122,6 +123,7 @@ function rangeslider(theme::WidgetTheme, vals::AbstractUnitRange{<:Integer}, for
                 tooltips: $tooltips,
                 connect: $connect,
                 orientation: $orientation,
+                direction: $direction,
                 format: {
                     to: function ( value ) {
                         var ind = Math.round(value-($min));

We'll get the Range Slider the bigger value is upper, smaller value is lower, with direction="rtl" option.

using Interact, Blink
win = Window();
ui = rangeslider(0:100; value=[30, 80], orientation="vertical", direction="rtl");
body!(win, ui)

Use stack for themes?

Ref is simple, but not good for modularity.

If in my package I have a strong preference of using Material design, then I'm going to do setbackend(Material()).

But once you use something from my package anything you do next will also be of Material theme!!

To bypass this I'd have to do something like, first reach into backend[] ref, save the current value, do setbackend, then setbackend with the saved value to leave it in a previous state.

If we used stacks, I could use a push! and pop!, and in the middle call some other package which may change the theme too.

Add dictionary with default class for each widget type

The dictionary should be overloadable by the WidgetTheme: this should simplify creating a new backend drastically. It should also allow to customize a theme using user css code or a more low level framework (e.g. Tachyons).

Build fails

On v0.10.2,

julia> versioninfo()
Julia Version 1.1.1
Commit 55e36cc308 (2019-05-16 04:10 UTC)
Platform Info:
  OS: Linux (x86_64-pc-linux-gnu)
  CPU: Intel(R) Core(TM) i7-5820K CPU @ 3.30GHz
  WORD_SIZE: 64
  LIBM: libopenlibm
  LLVM: libLLVM-6.0.1 (ORCJIT, haswell)
Environment:
  JULIA_EDITOR = emacsclient

(ConfabEnv) pkg> build InteractBase
  Building WebIO ─────── `~/ConfabDepot/packages/WebIO/Rk8wc/deps/build.log`
  Building Knockout ──── `~/ConfabDepot/packages/Knockout/JE2Yq/deps/build.log`
  Building InteractBase  `~/ConfabDepot/packages/InteractBase/l8cEC/deps/build.log`
┌ Error: Error building `InteractBase`: 
│   % Total    % Received % Xferd  Average Speed   Time    Time     Time  Current
│                                  Dload  Upload   Total   Spent    Left  Speed
100  664k  100  664k    0     0  2712k      0 --:--:-- --:--:-- --:--:-- 2712k
│   % Total    % Received % Xferd  Average Speed   Time    Time     Time  Current
│                                  Dload  Upload   Total   Spent    Left  Speed
  0     0    0     0    0     0      0      0 --:--:-- --:--:-- --:--:--     0
│ curl: (22) The requested URL returned error: 500 Internal Server Error
│ ERROR: LoadError: failed process: Process(`curl -g -L -f -o /home/cst-jean/ConfabDepot/packages/InteractBase/l8cEC/assets/prism.css https://www.gitcdn.xyz/repo/piever/InteractResources/v0.1.0/highlight/prism.css`, ProcessExited(22)) [22]
│ Stacktrace:
│  [1] error(::String, ::Base.Process, ::String, ::Int64, ::String) at ./error.jl:42
│  [2] pipeline_error at ./process.jl:785 [inlined]
│  [3] #run#515(::Bool, ::Function, ::Cmd) at ./process.jl:726
│  [4] run at ./process.jl:724 [inlined]
│  [5] download(::String, ::String) at ./download.jl:27
│  [6] top-level scope at /home/cst-jean/ConfabDepot/packages/InteractBase/l8cEC/deps/build.jl:18 [inlined]
│  [7] top-level scope at ./none:0
│  [8] include at ./boot.jl:326 [inlined]
│  [9] include_relative(::Module, ::String) at ./loading.jl:1038
│  [10] include(::Module, ::String) at ./sysimg.jl:29
│  [11] include(::String) at ./client.jl:403
│  [12] top-level scope at none:0in expression starting at /home/cst-jean/ConfabDepot/packages/InteractBase/l8cEC/deps/build.jl:17
└ @ Pkg.Operations /buildworker/worker/package_linux64/build/usr/share/julia/stdlib/v1.1/Pkg/src/Operations.jl:1075

Pasting the link in the browser gives me a 500 - internal server error.

slider rate and plotting - slider experience

I find the slider really useful for exploring data graphically. However, at present when using @manipulate for plots, the slider sometimes feels a bit laggy: If you click somewhere on the slider, then that particular index value is quickly evaluated, giving a rapid display.
But if you actually try to slide the slider, the only practical option is to slide rather slowly. A rapid slide at any point will lead to a freeze, followed by display of the plot for the final index value.

Here is an example using PyPlot:

using PyPlot, InteractBase
t = linspace(0,1,100) |>collect
x = linspace(-10,10,100) |>collect
f1 = figure(figsize=(10,2))
@manipulate for j in eachindex(t)
    withfig(f1,clear=true) do
        plot(x,sin.(t[j]*x))
    end
end

where the difference should be seen between moving the slider slowly, dragging rapidly to the end, and clicking to the end. Perhaps this is something to do with PyPlot or my laptop graphics, but at present the slider can feel quite clunky even for modest slide rates. I am curious as to whether others have this experience, especially if it persists on better hardware.

Would it be possible to change the behavior so that if the slide rate is faster than "slow" (whatever is continuously frame rendered), then the slider just serves up the final value, much like clicking on the slider would do. This would feel a lot more responsive to work with.

replace slider median with first?

Describe the bug
Using Slider with a default value of median feels unnatural for me. Would it be better to use first value as default?

To Reproduce
using @manipulate

Expected behavior
Slider value defaults to first value

Button text is displayed in uppercase when InteractUIkit is used

using CSSUtil
loadbutton = filepicker()
hellobutton = button("Hello!")
goodbyebutton = button("Good bye!")
ui = vbox( # put things one on top of the other
    loadbutton,
    hbox( # put things one next to the other
        pad(1em, hellobutton), # to allow some white space around the widget
        pad(1em, goodbyebutton),
    )
)
display(ui)

Function InteractBase.dropdown was about to overflow

Hi! I get an error using dropdown menus when trying to execute the example code from the API reference:

using InteractBulma, WebIO

options = Observable(["a", "b", "c"])
wdg = dropdown(options)

This gives the following error message and stacktrace:

ERROR: Function InteractBase.dropdown was about to overflow: check the signature
Stacktrace:
 [1] #dropdown#106(::Array{Any,1}, ::Function, ::InteractBulma.Bulma, ::Vararg{Any,N} where N) at /Users/lackner/.julia/v0.6/InteractBase/src/defaults.jl:10
 [2] dropdown(::InteractBulma.Bulma, ::Observables.Observable{Array{String,1}}) at /Users/lackner/.julia/v0.6/InteractBase/src/defaults.jl:10
 [3] #dropdown#106(::Array{Any,1}, ::Function, ::Observables.Observable{Array{String,1}}, ::Vararg{Observables.Observable{Array{String,1}},N} where N) at /Users/lackner/.julia/v0.6/InteractBase/src/defaults.jl:12
 [4] dropdown(::Observables.Observable{Array{String,1}}) at /Users/lackner/.julia/v0.6/InteractBase/src/defaults.jl:10
 [5] eval(::Module, ::Any) at ./boot.jl:235

a "recipe system" for GUIs

This is an issue to discuss the design of a "recipe" system for GUIs. What is necessary is a small light dependency package such that each package can define complex widgets to simplify usage (for example. GLM may add a way to select variables from a table with a dropdown, a modelling package could allow choosing some parameters with sliders / togglebuttons etc.). This implies (unless we recommend some other solution like Requires.jl) having a minimal package that is sufficient to define these complex widgets and is 100% reliable and solid dependency, tentatively called UIRecipesBase.

Option 1 (package of placeholders):

  • write placeholders for all the available widget functions (widget, input, slider, checkbox, etc...)
  • write placeholders for the helper functions to work with Vue (kwargs2vueprops, props2string...)
  • write placeholders for macro dom_str, Node, Observable, observe... (though actually Observables is so lightweight that maybe it can be included in the dependencies)
  • define the Widget type? this is actually a bit tricky, as the Widget type requires Node and Scope to type the fields, so it may be better to have a function that returns a Widget type and this function would have a placeholder in UIRecipesBase

I'm not very fond of this option as all JuliaGizmos packages would have to depend and extend this thing, which seems somewhat awkward.

Option 2 (overloading):

This is quite interesting, and would correspond to transforming all widgets into something that can be obtained as widget(type,...). We already have a function widget that allows to access most widgets (colorpicker, date picker, input, etc... The action plan would be as follows:

  • instead of slider, dropdown, textbox etc... define dispatches for widget(::Val{:slider}, ...) and then define slider(args....; kwargs...) = widget(::Val{:slider}, args..., kwargs...). This could be done by a macro:
@recipe function slider(args...; kwargs...)
# write function body here
end

that defines the dispatch and the shorthand slider. Though actually in InteractBase there's a place where it's very easy to define all of this, which is where I define the method without the first type argument (for the backend) for all widgets, so I could simply add it there.

  • the custom widget will then be a set of widget with some layout. The layout part is tricky: I would propose some sort of placeholder approach where we add a function node end placeholder (that WebIO extends to return Node) that users can use to create layout with flexboxes. Otherwise, we could add some placeholders for CSSUtil functions (hbox, vbox, hskip, vskip, hpad, etc...)

For this macro to work, the user would have to return a tuple of two elements: a node and an observable (or three elements if they want a primary scope) and then the macro would take care of defining the function that actually returns a widget object.

Defining type recipes would simply involve overloading widget with a custom type.

I'm personally in favor of option 2, but happy to discuss alternatives.

cc: @shashi

Unitful support

It would be great if widgets supported Unitful.jl, so e.g. sliders can be time values. It might be in an addon package, but this issue is just a reminder to think about that when designing types and methods.

widgets missing from documentation

I ordered them as they appear on the export lists

datepicker, timepicker, colorpicker, spinbox
input, textarea, togglecontent
tabs, checkboxes, toggles, tabulator

cheers

Typed widgets?

In Interact slider() produces an Interact.Slider.
InteractNext just outputs WebIO.Scope for every widget. If this is replacing InteractNext, what is the plan here?

Not having separate types means post-processing of widgets is difficult. I have a package that makes widgets and an interface from anything you throw at it, and reapplies signals back to the data, to save me rebuilding the interface every time I change my models:
https://github.com/rafaqz/AutoInteract.jl

But to make the layout passable you have to separate checkboxes/toggles from sliders etc somehow. In Interact that's easy, in InteractNext (and maybe this package?) it doesn't seem possible.

Fix dropdown layout

Using vbox to set the label is problematic for the downward arrow. Maybe even easier to put the label as placeholder?

Installation problem ... "EISDIR: illegal operation on a directory, read" upon "npm install"

Hi - I'm having an installation problem with InteractBase...

julia> versioninfo()
Julia Version 0.6.4
Commit 9d11f62bcb (2018-07-09 19:09 UTC)
Platform Info:
  OS: macOS (x86_64-apple-darwin14.5.0)
  CPU: Intel(R) Core(TM) i7-4980HQ CPU @ 2.80GHz
  WORD_SIZE: 64
  BLAS: libopenblas (USE64BITINT DYNAMIC_ARCH NO_AFFINITY Haswell MAX_THREADS=16)
  LAPACK: libopenblas64_
  LIBM: libopenlibm
  LLVM: libLLVM-3.9.1 (ORCJIT, haswell)

julia> Pkg.add("InteractBase")
< stuff above >
INFO: Building InteractBase
  % Total    % Received % Xferd  Average Speed   Time    Time     Time  Current
                                 Dload  Upload   Total   Spent    Left  Speed
100  664k  100  664k    0     0  3631k      0 --:--:-- --:--:-- --:--:-- 3631k
npm ERR! code EISDIR
npm ERR! errno -21
npm ERR! syscall read
npm ERR! EISDIR: illegal operation on a directory, read
< Failure notices below >

I can see in .julia/v0.6/InteractBase/deps/build.jl the failure happens at

run(`$npm install -y`)

and the failure happens when I run that by hand.

I tried adding --verbose to the command and it didn't shed much additional information.

julia> run(`$npm install --verbose`)
npm info it worked if it ends with ok
npm verb cli [ '/Users/lyon/.julia/v0.6/NodeJS/deps/bin/node-v8.10.0-darwin-x64/bin/node',
npm verb cli   '/Users/lyon/.julia/v0.6/NodeJS/deps/bin/node-v8.10.0-darwin-x64/lib/node_modules/npm/bin/npm-cli.js',
npm verb cli   'install',
npm verb cli   '--verbose' ]
npm info using [email protected]
npm info using [email protected]
npm verb config Skipping project config: /Users/lyon/.npmrc. (matches userconfig)
npm verb npm-session e2bcfb757c16565d
npm verb stack Error: EISDIR: illegal operation on a directory, read
npm verb cwd /Users/lyon/.julia/v0.6/InteractBase/deps
npm verb Darwin 17.6.0
npm verb argv "/Users/lyon/.julia/v0.6/NodeJS/deps/bin/node-v8.10.0-darwin-x64/bin/node" "/Users/lyon/.julia/v0.6/NodeJS/deps/bin/node-v8.10.0-darwin-x64/lib/node_modules/npm/bin/npm-cli.js" "install" "--verbose"
npm verb node v8.10.0
npm verb npm  v5.6.0
npm ERR! code EISDIR
npm ERR! errno -21
npm ERR! syscall read
npm ERR! EISDIR: illegal operation on a directory, read
npm verb exit [ -21, true ]

EISDIR seems to mean that it's trying to read a file that is actually a directory. I can't tell what it is trying to read.

Have you seen this before? I have a home-brew installed node and npm on my machine, but I don't think there's interference (for fun I tried using the same command with /usr/local/bin/npm and I get the same error).

Thanks in advance for any ideas! -- Adam

Add a file saver

Same as filepicker, to be used when the app runs in Blink, with Electron.

Cleaner support for PlotlyJS

Setting a PlotlyJS private variable on loading to embed the javascript in the html feels wrong, there should be a simpler way: maybe load the Plotly javascript in slap_design! ?

Naming nit-picks

This package is very cool!

I have some minor naming suggestions:

  1. CSSFramework -> something like WidgetTheme ? Because things like Material are not just CSS frameworks, they require some JS etc.
  2. setbackend -> settheme! -- daisy chains nicely with the "theme" above.
  3. The package itself maybe better as InteractBase -- let's makes Interact.jl depend on this and have a sensible default theme. InteractNext would become MaterialTheme.jl maybe, and then BulmaTheme.jl etc.

FR: Allow keyword for the color of `rangeslider`

The rangeslider widget is super-pretty!

You know what would be even prettier? Having it in many colors! It would be awesome if a keyword argument could let you specify a color for the slider! This teal-like color is really good but a choice would be even better!

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.