# Loading Icon Component for Phoenix LiveView

Today I am going to put together how to make a loading icon [LiveComponent](https://hexdocs.pm/phoenix_live_view/Phoenix.LiveComponent.html) for [Phoenix LiveView](https://hexdocs.pm/phoenix_live_view/Phoenix.LiveView.html).

## Get a loader CSS

First, I look for an open-source loader CSS because I am poor at designing and writing CSS. Luke Haas's [Single Element CSS Spinners](https://projects.lukehaas.me/css-loaders/) is nice.

## Make a loader CSS file

I create `assets/css/_loader.scss` file in my phoenix project and paste the loader CSS into that file.

I make sure that my loader CSS file is imported into `assets/css/app.scss` file.

```diff
+ @import 'loader';
```

## Make a loading icon component

First I make `lib/mnishiguchi_web/live/components/loading_component.ex` file. I make the component configurable for the CSS class name bacause I might want to use different loaders in different locations.

```elixir
defmodule MnishiguchiWeb.LoadingComponent do
  @moduledoc """
  Shows a loading icon.

  ## Examples

      <%= live_component @socket,
                          MnishiguchiWeb.LoadingComponent,
                          class: "loader7" %>

      <%= live_component @socket,
                          MnishiguchiWeb.LoadingComponent,
                          loading: @loading,
                          class: "loader7" %>

      <%= live_component @socket,
                          MnishiguchiWeb.LoadingComponent,
                          loading: !connected?(@socket),
                          class: "loader7" %>

  """

  use MnishiguchiWeb, :live_component

  @default_assigns %{
    loading: true,
    class: "loader"
  }

  @impl Phoenix.LiveComponent
  def update(assigns, socket) do
    socket =
      socket
      |> assign(@default_assigns)
      |> assign(assigns)

    {:ok, socket}
  end

  @impl Phoenix.LiveComponent
  def render(assigns) do
    ~L"""
    <%= if @loading do %>
      <div class="<%= @class %>">
        Loading...
      </div>
    <% end %>
    """
  end
end
```

That's it!

