laravel-frontend-presets/black-dashboard
Laravel frontend preset that scaffolds a Black Dashboard admin UI with Bootstrap layouts, authentication views, and ready-made dashboard pages. Install via Composer to quickly generate routes, controllers, and a sleek dark admin theme.
Black Dashboard is a scaffolding preset, not a runtime library. Its entire job is to dump Creative Tim’s Black Dashboard (Bootstrap 4 admin UI) views, SCSS, and compiled assets into a fresh Laravel app and wire up demo routes. You run it once, then the generated files are yours.
Minimal path:
composer create-project laravel/laravel my-app
cd my-app
composer require laravel-frontend-presets/black-dashboard
php artisan ui black-dashboard # optionally: --auth
npm install
npm run build # or: npm run dev
php artisan migrate
php artisan serve
Before you type php artisan ui black-dashboard, open the package’s service provider to confirm what it actually overwrites and which build tool it targets:
vendor/laravel-frontend-presets/black-dashboard/src/BlackDashboardPresetServiceProvider.php
That file lists the stub callbacks (updateViews, updateRoutes, updateSass, updateWebpack/updateVite, asset publishing). It is more reliable than the README, which lags the code on this repo.
Where to look first
routes/web.php — the demo /dashboard, /tables, /login routes the preset injected.resources/views/layouts/ and resources/views/dashboard.blade.php — the master shell (.wrapper > .sidebar + .main-panel) and the stat-card/table demo page.resources/sass/black-dashboard.scss — the imports for Bootstrap 4 and the Black Dashboard partials.public/assets/ (or public/vendor/...) — prebuilt CSS/JS/fonts; if these are missing, icons and the sidebar will silently break.First real use case: replace the hard-coded demo table in dashboard.blade.php with live data. Swap the static <tr> block for an @foreach ($orders as $order) over a paginated Eloquent query, keep the existing table classes, and point your /dashboard route at a controller instead of a closure. That single change turns the preset from a mockup into your app shell.
Treat the output as application code, immediately. Commit the generated resources/views, resources/sass, and resources/js before writing a single feature. The preset is a one-shot generator; re-running php artisan ui black-dashboard on a customized app overwrites your work.
Extract the shell into a layout + partials. The generated pages duplicate the sidebar and navbar markup. Normalize to:
{{-- resources/views/layouts/app.blade.php --}}
@include('layouts.partials.sidebar')
<div class="main-panel">
@include('layouts.partials.navbar')
<div class="content">
<div class="container-fluid">@yield('content')</div>
</div>
</div>
Drive the active nav state off the router rather than hand-editing classes:
<li class="nav-item {{ request()->routeIs('orders.*') ? 'active' : '' }}">
<a class="nav-link" href="{{ route('orders.index') }}">Orders</a>
</li>
Convert repeated card markup to anonymous components. Black Dashboard pages repeat .card > .card-header > .card-body dozens of times; <x-card title="..."> and <x-stat-card color="primary" :value="$count" /> keep views readable and make a theme swap tractable later.
Respect the exact DOM contract. Black Dashboard’s CSS and perfect-scrollbar are coupled to specific wrapper classes and nesting: .wrapper, .sidebar[data-color], .main-panel, .content, .navbar-wrapper. Swapping <div class="content"> for a semantic <main> will break layout and scrollbars. Copy structure verbatim from the demo pages; change content, not scaffolding.
Keep the JS dependency chain intact. Black Dashboard’s vendor bundle (perfect-scrollbar, bootstrap-datetimepicker, SweetAlert, jQuery plugins) expects jQuery on window before the plugins load. If you move to Vite, import order matters:
import $ from 'jquery'
window.$ = window.jQuery = $
import 'bootstrap' // Bootstrap 4, needs Popper
import './black-dashboard' // preset's init script
import '../sass/black-dashboard.scss'
Move the inline <script> blocks out of dashboard.blade.php (the Chart.js and sidebar-toggle init) into resources/js/ and guard them — they assume elements exist and throw on pages that don’t include those canvases.
Data-driven pages. For tables, keep the preset’s <table class="table"> and drop in pagination. Laravel’s default paginator is Tailwind-flavored; publish and override it (php artisan vendor:publish --tag=laravel-pagination) to emit Bootstrap 4 page-item/page-link markup. The same applies to validation errors in auth/* views: Black Dashboard styles form controls with form-group/is-invalid, not @error defaults.
Auth scaffolding. If the preset’s --auth flag ships views, use them. If not, composer require laravel/ui && php artisan ui bootstrap --auth gives you Bootstrap 4-compatible auth views, then restyle resources/views/auth/login.blade.php into Black Dashboard’s centered card layout. Do not install Breeze or Jetstream afterwards — they rewrite resources/js/app.js, vite.config.js, and the root view around Tailwind/Alpine and will fight this preset.
Composition with Livewire. Livewire is the cleanest fit: keep Black Dashboard as the Blade shell, add @livewireStyles/@livewireScripts, and let components re-render tables and forms. Avoid Inertia/Vue/React here — the preset’s jQuery plugins expect server-rendered DOM and don’t survive client-side navigation without manual re-init.
Multi-project reuse. Since the preset is just stubs behind Laravel\Ui\Ui::install('black-dashboard', ...), you can register your own internal preset (fork the stubs, custom sidebar, branded colors) and get consistent scaffolding across projects with one php artisan ui acme-dashboard.
php artisan ui requires laravel/ui. Laravel 11 does not ship it. The preset declares it as a dependency, but if you’ve pruned it or are on a non-standard install, the command simply won’t exist and you’ll waste time debugging. Check php artisan list | grep ui first.routes/web.php, resources/views/welcome.blade.php, resources/sass/app.scss, resources/js/app.js, and occasionally webpack.mix.js/vite.config.js. Run it on a clean checkout, never on an existing app, never in production.@vite(...) while the preset wrote mix(...) (or vice versa), you get unstyled pages with no error. Symptom: HTML loads, CSS 404s. Fix: inspect the layout for the directive, confirm public/build/manifest.json exists after npm run build.public/assets/fonts but the CSS expects ../fonts/, every sidebar and stat-card icon renders as an empty box. Check public/ after install; the package may require an explicit php artisan vendor:publish.data-toggle/data-target, not data-bs-*. Adding a Bootstrap 5 CDN “to get a component working” will break modals and dropdowns. Popper is required and must load before Bootstrap JS.ReferenceError: $ is not defined inside a Black Dashboard plugin means the vendor bundle loaded before your jQuery assignment. Set window.$/window.jQuery at the top of app.js.--auth output (or laravel/ui fallback) is generic Bootstrap; Black Dashboard’s login is a full-height .card layout. Budget time to restyle auth/login, auth/register, auth/passwords/*, and the layouts/app header dropdown.php artisan view:clear && php artisan config:clear. If your edits to a partial don’t appear, this is almost always why.composer remove laravel-frontend-presets/black-dashboard (and delete the published stubs) keeps your dependency tree honest. If you keep it, pin the version — 87 stars and zero dependents means very little community validation, and a minor release could quietly change stub contents. Diff releases before upgrading.php artisan ui black-dashboard -vvv and read the service provider’s callback list to see exactly which files it touched. If it silently no-ops, your Ui::install registration isn’t booting — check package discovery (composer dump-autoload, php artisan package:discover).How can I help you explore Laravel packages today?