Packages

phoenix_kit

1.6.4
1.7.210 1.7.209 1.7.208 1.7.207 1.7.206 1.7.205 1.7.204 1.7.203 1.7.202 1.7.201 1.7.200 1.7.199 1.7.198 1.7.197 1.7.196 1.7.194 1.7.193 1.7.192 1.7.191 1.7.190 1.7.189 1.7.187 1.7.186 1.7.185 1.7.184 1.7.183 1.7.182 1.7.181 1.7.180 1.7.179 1.7.178 1.7.177 1.7.176 1.7.175 1.7.174 1.7.173 1.7.172 1.7.171 1.7.170 1.7.169 1.7.168 1.7.167 1.7.166 1.7.165 1.7.164 1.7.162 1.7.161 1.7.160 1.7.159 1.7.157 1.7.156 1.7.155 1.7.154 1.7.153 1.7.152 1.7.151 1.7.150 1.7.149 1.7.146 1.7.145 1.7.144 1.7.143 1.7.138 1.7.133 1.7.132 1.7.131 1.7.130 1.7.128 1.7.126 1.7.125 1.7.121 1.7.120 1.7.119 1.7.118 1.7.117 1.7.116 1.7.115 1.7.114 1.7.113 1.7.112 1.7.111 1.7.110 1.7.109 1.7.108 1.7.107 1.7.106 1.7.105 1.7.104 1.7.103 1.7.102 1.7.101 1.7.100 1.7.99 1.7.98 1.7.97 1.7.96 1.7.95 1.7.94 1.7.93 1.7.92 1.7.91 1.7.90 1.7.89 1.7.88 1.7.87 1.7.86 1.7.85 1.7.84 1.7.83 1.7.82 1.7.81 1.7.80 1.7.79 1.7.78 1.7.77 1.7.76 1.7.75 1.7.74 1.7.71 1.7.70 1.7.69 1.7.66 1.7.65 1.7.64 1.7.63 1.7.62 1.7.61 1.7.59 1.7.58 1.7.57 1.7.56 1.7.55 1.7.54 1.7.53 1.7.52 1.7.51 1.7.49 1.7.44 1.7.43 1.7.42 1.7.41 1.7.39 1.7.38 1.7.37 1.7.36 1.7.34 1.7.33 1.7.31 1.7.30 1.7.29 1.7.28 1.7.27 1.7.26 1.7.25 1.7.24 1.7.23 1.7.22 1.7.21 1.7.20 1.7.19 1.7.18 1.7.17 1.7.16 1.7.15 1.7.14 1.7.13 1.7.12 1.7.11 1.7.10 1.7.9 1.7.8 1.7.7 1.7.6 1.7.5 1.7.4 1.7.3 1.7.2 1.7.1 1.7.0 1.6.20 1.6.19 1.6.18 1.6.17 1.6.16 1.6.15 1.6.14 1.6.13 1.6.12 1.6.11 1.6.10 1.6.9 1.6.8 1.6.7 1.6.6 1.6.5 1.6.4 1.6.3 1.5.2 1.5.1 1.5.0 1.4.9 1.4.8 1.4.7 1.4.6 1.4.5 1.4.4 1.4.3 1.4.2 1.4.1 1.4.0 1.3.2 1.3.1 1.3.0 1.2.10 1.2.9 1.2.8 1.2.7 1.2.5 1.2.4 1.2.2 1.2.1 1.2.0 1.1.0 1.0.0

A foundation for building Elixir Phoenix apps — SaaS, social networks, ERP systems, marketplaces, and more

Current section

Files

Jump to
phoenix_kit lib phoenix_kit_web live users media.html.heex
Raw

lib/phoenix_kit_web/live/users/media.html.heex

<PhoenixKitWeb.Components.LayoutWrapper.app_layout
flash={@flash}
phoenix_kit_current_scope={assigns[:phoenix_kit_current_scope]}
page_title="Media"
current_path={@url_path}
project_title={@project_title}
current_locale={@current_locale}
>
<div class="p-6">
<div class="mb-8">
<h1 class="text-3xl font-bold text-base-content">Media</h1>
<p class="text-base-content/70 mt-1">Manage user media and uploads</p>
</div>
<%!-- Upload Section (Hidden by default) --%>
<%= if @show_upload do %>
<div class="card bg-base-100 shadow-xl mb-8 animate-in fade-in duration-200">
<div class="card-body">
<h2 class="card-title text-xl mb-4">Upload Media</h2>
<p class="text-sm text-base-content/70 mb-4">
Upload images, videos, or PDFs. Files are automatically processed and optimized.
</p>
<.file_upload
upload={@uploads.media_files}
label="Upload Media Files"
icon="hero-cloud-arrow-up"
accept_description="JPG, PNG, WebP, MP4, WebM, PDF"
max_size_description="100MB per file"
/>
</div>
</div>
<% end %>
<%!-- Uploaded Files --%>
<%= if @total_count > 0 do %>
<div class="card bg-base-100 shadow-xl">
<div class="card-body">
<div class="flex justify-between items-center mb-4">
<div class="flex items-center gap-3">
<h2 class="card-title text-xl">Uploaded Files ({@total_count})</h2>
<button
phx-click="toggle_upload"
class={["btn btn-sm gap-2", (@show_upload && "btn-error") || "btn-primary"]}
>
<%= if @show_upload do %>
<.icon name="hero-x-mark" class="w-4 h-4" /> Cancel
<% else %>
<.icon name="hero-plus" class="w-4 h-4" /> Add Media
<% end %>
</button>
</div>
<.pagination_info
page={@current_page}
per_page={@per_page}
total_count={@total_count}
/>
</div>
<div class="grid grid-cols-3 md:grid-cols-5 lg:grid-cols-6 gap-3">
<%= for file <- @uploaded_files do %>
<.link
navigate={PhoenixKit.Utils.Routes.path("/admin/users/media/#{file.file_id}")}
class="group relative aspect-square bg-base-300 rounded-lg overflow-hidden cursor-pointer hover:shadow-lg transition-shadow"
>
<% image_url = file.urls["medium"] || file.urls["original"] %>
<%= if image_url do %>
<img
src={image_url}
alt={file.filename}
class="w-full h-full object-cover pointer-events-none group-hover:opacity-75 transition-opacity"
onerror="this.parentElement.querySelector('.image-error-placeholder').style.display='grid';"
/>
<div class="image-error-placeholder hidden absolute inset-0 bg-base-300 grid place-items-center text-base-content/50">
<div class="flex flex-col items-center justify-center">
<.icon name="hero-photo" class="w-12 h-12 mb-2 text-error" />
<p class="text-xs font-semibold">Image Missing</p>
</div>
</div>
<% else %>
<div class="flex flex-col items-center justify-center w-full h-full text-base-content/50 group-hover:bg-base-200 transition-colors">
<.icon name={file_icon(file.file_type)} class="w-12 h-12 mb-2" />
<p class="text-sm font-semibold">{String.upcase(file.file_type)}</p>
</div>
<% end %>
<%!-- File size in corner --%>
<div class="absolute bottom-2 right-2 bg-black/60 text-white text-xs px-2 py-1 rounded pointer-events-none">
{format_file_size(file.size)}
</div>
</.link>
<% end %>
</div>
<%!-- Pagination Controls --%>
<%= if @total_count > @per_page do %>
<.pagination
current_page={@current_page}
total_pages={@total_pages}
base_path={@url_path}
/>
<% end %>
</div>
</div>
<% else %>
<div class="card bg-base-100 shadow-xl">
<div class="card-body">
<div class="flex items-center gap-3 mb-4">
<h2 class="card-title text-xl">Uploaded Files</h2>
<button
phx-click="toggle_upload"
class={["btn btn-sm gap-2", (@show_upload && "btn-error") || "btn-primary"]}
>
<%= if @show_upload do %>
<.icon name="hero-x-mark" class="w-4 h-4" /> Cancel
<% else %>
<.icon name="hero-plus" class="w-4 h-4" /> Add Media
<% end %>
</button>
</div>
<div class="bg-base-200 rounded-lg p-8 text-center">
<p class="text-base-content/70">
No media uploaded yet. Upload your first file above!
</p>
</div>
</div>
</div>
<% end %>
</div>
</PhoenixKitWeb.Components.LayoutWrapper.app_layout>