defmodule FloUI.SelectionListItem do @moduledoc """ ## Usage in SnapFramework A selection list item used by SelectionList. data is a tuple in the form of ``` elixir {label, value, id} ``` ``` elixir <%= graph font_size: 20 %> <%= component FloUI.SelectionListItem, {@label, @value, @key} %> ``` """ @default_theme FloUI.Theme.preset(:primary) use SnapFramework.Component, name: :selection_list_item, template: "lib/selection_list/selection_list_item.eex", controller: FloUI.SelectionListItemController, assigns: [ hovered: false, width: 500, height: 50 ], opts: [] defcomponent(:selection_list_item, :tuple) watch([:hovered]) use_effect([assigns: [selected: :any]], run: [:on_selected_change] ) @impl true def setup(%{assigns: %{data: {label, value, key}, hovered: hovered, opts: opts}} = scene) do request_input(scene, [:cursor_pos]) assign(scene, label: label, value: value, key: key, width: opts[:width] || 500, selected: opts[:selected] || false, hovered: hovered, theme: get_theme(opts) ) end @impl true def bounds(_data, opts) do {0.0, 0.0, opts[:width] || 500, 50} end @impl true def process_input({:cursor_pos, _}, :box, scene) do {:noreply, assign(scene, hovered: true)} end def process_input({:cursor_pos, _}, _, scene) do {:noreply, assign(scene, hovered: false)} end def process_input( {:cursor_button, {:btn_left, 1, _, _}}, :box, %{assigns: %{key: key, label: label, value: value, selected: false}} = scene ) do send_parent_event(scene, {:select, {label, value, key}}) {:noreply, assign(scene, selected: true)} end def process_input( {:cursor_button, {:btn_left, 1, _, _}}, :box, %{assigns: %{selected: true}} = scene ) do send_parent_event(scene, :deselect) {:noreply, assign(scene, selected: false)} end def process_input(_, _, scene) do {:noreply, scene} end @impl true def process_call(:deselect, _, scene) do {:reply, :ok, assign(scene, selected: false)} end defp get_theme(opts) do case opts[:theme] do nil -> @default_theme :dark -> @default_theme :light -> @default_theme theme -> theme end |> FloUI.Theme.normalize() end end