defmodule PUI.Container do
@moduledoc """
Container components for organizing content with consistent styling.
## Card
Basic card container:
<.card>
Card content goes here
## Card with Header
<.card>
<.card_header>
<.card_title>Card Title
<.card_description>Card description
## Full Card Example
<.card>
<.card_header>
<.card_title>Profile
<.card_description>Manage your account settings
<.card_action>
<.button size="sm">Edit
<.card_content>
Your profile information goes here.
<.card_footer>
<.button variant="outline">Cancel
<.button>Save Changes
## Custom Styling
<.card class="bg-blue-50 border-blue-200">
Card with custom colors
## Icon
Render Heroicons:
<.icon name="hero-check-circle" />
<.icon name="hero-x-mark" class="w-5 h-5" />
## Components
| Component | Description |
|-----------|-------------|
| `card/1` | Main card container |
| `card_header/1` | Card header section |
| `card_title/1` | Card title text |
| `card_description/1` | Card subtitle/description |
| `card_action/1` | Action buttons in header (right-aligned) |
| `card_content/1` | Main content area |
| `card_footer/1` | Footer section |
| `header/1` | Page header component |
| `icon/1` | Heroicon component |
"""
use Phoenix.Component
attr :class, :string, default: ""
attr :rest, :global
slot :inner_block
def card(assigns) do
~H"""
{render_slot(@inner_block)}
"""
end
slot :inner_block
def card_header(assigns) do
~H"""
"""
end
attr :class, :string, default: ""
slot :inner_block
def card_title(assigns) do
~H"""
{render_slot(@inner_block)}
"""
end
@doc """
Renders a header with title.
"""
slot :inner_block, required: true
slot :subtitle
slot :actions
def header(assigns) do
~H"""
{render_slot(@inner_block)}
{render_slot(@subtitle)}
{render_slot(@actions)}
"""
end
attr :class, :string, default: ""
slot :inner_block
def card_description(assigns) do
~H"""
{render_slot(@inner_block)}
"""
end
slot :inner_block
def card_action(assigns) do
~H"""
{render_slot(@inner_block)}
"""
end
slot :inner_block
def card_content(assigns) do
~H"""
{render_slot(@inner_block)}
"""
end
attr :class, :string, default: ""
slot :inner_block
def card_footer(assigns) do
~H"""
{render_slot(@inner_block)}
"""
end
@doc """
ported from core components
Renders a [Heroicon](https://heroicons.com).
Heroicons come in three styles – outline, solid, and mini.
By default, the outline style is used, but solid and mini may
be applied by using the `-solid` and `-mini` suffix.
You can customize the size and colors of the icons by setting
width, height, and background color classes.
Icons are extracted from the `deps/heroicons` directory and bundled within
your compiled app.css by the plugin in `assets/vendor/heroicons.js`.
## Examples
<.icon name="hero-x-mark" />
<.icon name="hero-arrow-path" class="ml-1 size-3 motion-safe:animate-spin" />
"""
attr :name, :string, required: true
attr :class, :string, default: "size-4"
attr :rest, :global
def icon(%{name: "hero-" <> _} = assigns) do
~H"""
"""
end
end