PhiaUi.Components.TagsInput (phia_ui v0.1.17)

Copy Markdown View Source

Tags input component for PhiaUI.

Provides tags_input/1 — a multi-tag input field that renders existing tags as removable badge chips and lets users add new tags by typing and pressing Enter (or a configurable separator character).

Tags are managed client-side by the PhiaTagsInput JS hook, which handles:

  • Adding a tag on Enter or separator key
  • Removing a tag via the × button or Backspace on an empty input
  • Deduplication (ignores duplicate values)
  • Syncing the hidden <input> with the current tag CSV for form submission

The component integrates with Phoenix.HTML.FormField so changeset validation errors are displayed automatically.

When to use

Use tags_input/1 for any field that accepts a variable number of string values — article labels, skill tags, email recipients, keyword lists, etc.

Registration

Register the hook in app.js:

import PhiaTagsInput from "./hooks/tags_input"
let liveSocket = new LiveSocket("/live", Socket, {
  hooks: { PhiaTagsInput }
})

Basic form example

<.form for={@form} phx-submit="save_article">
  <.tags_input
    field={@form[:tags]}
    label="Tags"
    placeholder="Add a tag..."
  />
  <.button type="submit">Save</.button>
</.form>

Custom separator

By default, pressing , (comma) or Enter adds a tag. You can change the separator to ; or any other character:

<.tags_input
  field={@form[:emails]}
  label="Recipients"
  placeholder="Type an email and press Enter..."
  separator=";"
/>

Value formats

The component accepts the field value in either format:

FormatExample
CSV string"elixir,phoenix,liveview"
List of strings["elixir", "phoenix"]

Empty strings and whitespace-only values are filtered out automatically.

Changeset integration

Tags are serialised as a comma-separated string in the hidden input. In your changeset, cast and split the CSV field:

defmodule MyApp.Article do
  use Ecto.Schema
  import Ecto.Changeset

  schema "articles" do
    field :tags, {:array, :string}
  end

  def changeset(article, attrs) do
    # tags arrive as CSV string "elixir,phoenix" from the form
    tags =
      case attrs["tags"] do
        nil -> []
        csv -> String.split(csv, ",", trim: true)
      end

    article
    |> cast(Map.put(attrs, "tags", tags), [:tags])
    |> validate_required([:tags])
  end
end

Alternatively, store tags as a single delimited string and split on read.

Summary

Functions

Renders a multi-tag input integrated with Phoenix.HTML.FormField.

Functions

tags_input(assigns)

Renders a multi-tag input integrated with Phoenix.HTML.FormField.

Initial tags are parsed from field.value (list or CSV string) and rendered server-side. The PhiaTagsInput hook takes over on mount and manages all client-side add/remove/dedup/sync behaviour.

The hidden <input> is kept in sync by the hook and carries the current tag CSV on form submit, which the changeset receives as a string.

Attributes

  • field (Phoenix.HTML.FormField) (required) - A Phoenix.HTML.FormField from @form[:field_name]. Provides id, name, value, and errors for full form integration.

  • label (:string) - Label text rendered above the input. Pass nil to omit the label. Defaults to nil.

  • placeholder (:string) - Placeholder text shown in the text input when it is empty. Defaults to "Add tag...".

  • separator (:string) - Character that triggers adding the current input value as a new tag, in addition to the Enter key. Defaults to ",". The PhiaTagsInput hook reads this from data-separator.

    Defaults to ",".

  • class (:string) - Additional CSS classes for the outer wrapper div. Defaults to nil.