init language
This commit is contained in:
parent
2ab0549f02
commit
7b38c511ce
|
|
@ -0,0 +1,30 @@
|
||||||
|
<?php
|
||||||
|
|
||||||
|
namespace App\Http\Controllers;
|
||||||
|
|
||||||
|
use Illuminate\Http\Request;
|
||||||
|
use Illuminate\Http\JsonResponse;
|
||||||
|
use Illuminate\Support\Facades\App;
|
||||||
|
use Illuminate\Support\Facades\Session;
|
||||||
|
|
||||||
|
class LocaleController extends Controller
|
||||||
|
{
|
||||||
|
/**
|
||||||
|
* Handle language switching request.
|
||||||
|
*
|
||||||
|
* @param \Illuminate\Http\Request $request
|
||||||
|
* @return \Illuminate\Http\JsonResponse
|
||||||
|
*/
|
||||||
|
public function switch(Request $request): JsonResponse
|
||||||
|
{
|
||||||
|
$locale = $request->input('locale');
|
||||||
|
|
||||||
|
// Validate locale
|
||||||
|
if (in_array($locale, ['en', 'id'])) {
|
||||||
|
App::setLocale($locale);
|
||||||
|
Session::put('locale', $locale);
|
||||||
|
}
|
||||||
|
|
||||||
|
return response()->json(['success' => true]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,43 @@
|
||||||
|
<?php
|
||||||
|
|
||||||
|
namespace App\Http\Middleware;
|
||||||
|
|
||||||
|
use Closure;
|
||||||
|
use Illuminate\Http\Request;
|
||||||
|
use Illuminate\Support\Facades\App;
|
||||||
|
use Illuminate\Support\Facades\Session;
|
||||||
|
|
||||||
|
class SetLocale
|
||||||
|
{
|
||||||
|
/**
|
||||||
|
* Handle an incoming request.
|
||||||
|
*
|
||||||
|
* @param \Illuminate\Http\Request $request
|
||||||
|
* @param \Closure $next
|
||||||
|
* @return mixed
|
||||||
|
*/
|
||||||
|
public function handle(Request $request, Closure $next)
|
||||||
|
{
|
||||||
|
// Check if locale is in request
|
||||||
|
if ($request->has('locale')) {
|
||||||
|
$locale = $request->get('locale');
|
||||||
|
|
||||||
|
// Validate locale
|
||||||
|
if (in_array($locale, ['en', 'id'])) {
|
||||||
|
App::setLocale($locale);
|
||||||
|
Session::put('locale', $locale);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Check if locale is in session
|
||||||
|
elseif (Session::has('locale')) {
|
||||||
|
$locale = Session::get('locale');
|
||||||
|
|
||||||
|
if (in_array($locale, ['en', 'id'])) {
|
||||||
|
App::setLocale($locale);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return $next($request);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
@ -11,7 +11,9 @@ return Application::configure(basePath: dirname(__DIR__))
|
||||||
health: '/up',
|
health: '/up',
|
||||||
)
|
)
|
||||||
->withMiddleware(function (Middleware $middleware): void {
|
->withMiddleware(function (Middleware $middleware): void {
|
||||||
//
|
$middleware->web(append: [
|
||||||
|
\App\Http\Middleware\SetLocale::class,
|
||||||
|
]);
|
||||||
})
|
})
|
||||||
->withExceptions(function (Exceptions $exceptions): void {
|
->withExceptions(function (Exceptions $exceptions): void {
|
||||||
//
|
//
|
||||||
|
|
|
||||||
|
|
@ -3,6 +3,6 @@
|
||||||
return [
|
return [
|
||||||
|
|
||||||
'id' => 'Indonesia',
|
'id' => 'Indonesia',
|
||||||
'en' => 'English'
|
'en' => 'English',
|
||||||
|
|
||||||
];
|
];
|
||||||
|
|
|
||||||
|
|
@ -0,0 +1,6 @@
|
||||||
|
<?php
|
||||||
|
|
||||||
|
return [
|
||||||
|
'new_arrivals' => 'New Arrivals',
|
||||||
|
'meet_the_collection' => 'Meet the :app collection'
|
||||||
|
];
|
||||||
|
|
@ -0,0 +1,9 @@
|
||||||
|
<?php
|
||||||
|
|
||||||
|
return [
|
||||||
|
'this_weeks_highlights' => 'This week\'s highlights',
|
||||||
|
'best_sellers' => 'Best sellers',
|
||||||
|
'new_arrivals' => 'New arrivals',
|
||||||
|
'sale_items' => 'Sale items',
|
||||||
|
'top_rated' => 'Top rated'
|
||||||
|
];
|
||||||
|
|
@ -3,6 +3,6 @@
|
||||||
return [
|
return [
|
||||||
|
|
||||||
'id' => 'Indonesia',
|
'id' => 'Indonesia',
|
||||||
'en' => 'English'
|
'en' => 'English',
|
||||||
|
|
||||||
];
|
];
|
||||||
|
|
|
||||||
|
|
@ -0,0 +1,6 @@
|
||||||
|
<?php
|
||||||
|
|
||||||
|
return [
|
||||||
|
'new_arrivals' => 'Kedatangan Baru',
|
||||||
|
'meet_the_collection' => 'Temukan koleksi :app'
|
||||||
|
];
|
||||||
|
|
@ -0,0 +1,9 @@
|
||||||
|
<?php
|
||||||
|
|
||||||
|
return [
|
||||||
|
'this_weeks_highlights' => 'Highlight minggu ini',
|
||||||
|
'best_sellers' => 'Terlaris',
|
||||||
|
'new_arrivals' => 'Kedatangan baru',
|
||||||
|
'sale_items' => 'Item diskon',
|
||||||
|
'top_rated' => 'Peringkat tertinggi'
|
||||||
|
];
|
||||||
|
|
@ -1,8 +1,8 @@
|
||||||
<!-- Special collection carousel -->
|
<!-- Special collection carousel -->
|
||||||
<section class="container pb-5 mb-2 mb-sm-3 mb-lg-4 mb-xl-5">
|
<section class="container pb-5 mb-2 mb-sm-3 mb-lg-4 mb-xl-5">
|
||||||
<div class="d-md-none text-center pb-3 mb-3">
|
<div class="d-md-none text-center pb-3 mb-3">
|
||||||
<p class="mb-2">New arrivals</p>
|
<p class="mb-2">{{ __('new_arrivals.new_arrivals') }}</p>
|
||||||
<h2 class="mb-0">Meet the {{ config('app.name') }} collection</h2>
|
<h2 class="mb-0">{{ __('new_arrivals.meet_the_collection', ['app' => config('app.name')]) }}</h2>
|
||||||
</div>
|
</div>
|
||||||
<div class="row align-items-center pb-xxl-3">
|
<div class="row align-items-center pb-xxl-3">
|
||||||
|
|
||||||
|
|
@ -34,8 +34,8 @@
|
||||||
<!-- Products master slider -->
|
<!-- Products master slider -->
|
||||||
<div class="col-md-5 order-md-1 text-center">
|
<div class="col-md-5 order-md-1 text-center">
|
||||||
<div class="d-none d-md-block pb-3 mb-2 mb-lg-3 mx-auto" style="max-width: 306px">
|
<div class="d-none d-md-block pb-3 mb-2 mb-lg-3 mx-auto" style="max-width: 306px">
|
||||||
<p class="mb-2">New arrivals</p>
|
<p class="mb-2">{{ __('new_arrivals.new_arrivals') }}</p>
|
||||||
<h2 class="mb-0">Meet the Cartzilla collection</h2>
|
<h2 class="mb-0">{{ __('new_arrivals.meet_the_collection', ['app' => config('app.name')]) }}</h2>
|
||||||
</div>
|
</div>
|
||||||
<div class="d-flex align-items-center justify-content-center">
|
<div class="d-flex align-items-center justify-content-center">
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -1,21 +1,21 @@
|
||||||
<section class="container pb-5 mb-2 mb-sm-3 mb-lg-4 mb-xl-5">
|
<section class="container pb-5 mb-2 mb-sm-3 mb-lg-4 mb-xl-5">
|
||||||
<h2 class="text-center pb-2 pb-sm-3">This week's highlights</h2>
|
<h2 class="text-center pb-2 pb-sm-3">{{ __('weeks_highlights.this_weeks_highlights') }}</h2>
|
||||||
|
|
||||||
<!-- Nav pills -->
|
<!-- Nav pills -->
|
||||||
<div class="row g-0 overflow-x-auto pb-2 pb-sm-3 mb-3">
|
<div class="row g-0 overflow-x-auto pb-2 pb-sm-3 mb-3">
|
||||||
<div class="col-auto pb-1 pb-sm-0 mx-auto">
|
<div class="col-auto pb-1 pb-sm-0 mx-auto">
|
||||||
<ul class="nav nav-pills flex-nowrap text-nowrap">
|
<ul class="nav nav-pills flex-nowrap text-nowrap">
|
||||||
<li class="nav-item">
|
<li class="nav-item">
|
||||||
<a class="nav-link active" aria-current="page" href="#!">Best sellers</a>
|
<a class="nav-link active" aria-current="page" href="#!">{{ __('weeks_highlights.best_sellers') }}</a>
|
||||||
</li>
|
</li>
|
||||||
<li class="nav-item">
|
<li class="nav-item">
|
||||||
<a class="nav-link" href="#!">New arrivals</a>
|
<a class="nav-link" href="#!">{{ __('weeks_highlights.new_arrivals') }}</a>
|
||||||
</li>
|
</li>
|
||||||
<li class="nav-item">
|
<li class="nav-item">
|
||||||
<a class="nav-link" href="#!">Sale items</a>
|
<a class="nav-link" href="#!">{{ __('weeks_highlights.sale_items') }}</a>
|
||||||
</li>
|
</li>
|
||||||
<li class="nav-item">
|
<li class="nav-item">
|
||||||
<a class="nav-link" href="#!">Top rated</a>
|
<a class="nav-link" href="#!">{{ __('weeks_highlights.top_rated') }}</a>
|
||||||
</li>
|
</li>
|
||||||
</ul>
|
</ul>
|
||||||
</div>
|
</div>
|
||||||
|
|
|
||||||
|
|
@ -1,22 +1,48 @@
|
||||||
<!-- Language selector for sidebar/offcanvas -->
|
<!-- Language selector for sidebar/offcanvas -->
|
||||||
<div class="dropdown nav">
|
<div class="dropdown nav">
|
||||||
<a class="nav-link dropdown-toggle py-1 px-0" href="#" data-bs-toggle="dropdown" aria-haspopup="true" aria-expanded="false" aria-label="{{ __('messages.Country select') }}: USA">
|
<a class="nav-link dropdown-toggle py-1 px-0" href="#" data-bs-toggle="dropdown" aria-haspopup="true" aria-expanded="false" aria-label="{{ __('languages.Country select') }}: {{ app()->getLocale() === 'en' ? 'USA' : 'Indonesia' }}">
|
||||||
<div class="ratio ratio-1x1" style="width: 20px">
|
<div class="ratio ratio-1x1" style="width: 20px">
|
||||||
<img src="/img/flags/en-us.png" alt="USA">
|
<img src="/img/flags/{{ app()->getLocale() === 'en' ? 'en-us' : 'id' }}.png" alt="{{ app()->getLocale() === 'en' ? 'USA' : 'Indonesia' }}">
|
||||||
</div>
|
</div>
|
||||||
</a>
|
</a>
|
||||||
<ul class="dropdown-menu fs-sm" style="--cz-dropdown-spacer: .5rem">
|
<ul class="dropdown-menu fs-sm" style="--cz-dropdown-spacer: .5rem">
|
||||||
<li>
|
<li>
|
||||||
<a class="dropdown-item" href="#!">
|
<a class="dropdown-item {{ app()->getLocale() === 'en' ? 'active' : '' }}" href="#" onclick="switchLanguageSidebar('en')">
|
||||||
<img src="/img/flags/en-us.png" class="flex-shrink-0 me-2" width="20" alt="United States">
|
<img src="/img/flags/en-us.png" class="flex-shrink-0 me-2" width="20" alt="United States">
|
||||||
{{ __('languages.en') }}
|
{{ __('languages.en') }}
|
||||||
</a>
|
</a>
|
||||||
</li>
|
</li>
|
||||||
|
|
||||||
<li>
|
<li>
|
||||||
<a class="dropdown-item" href="#!">
|
<a class="dropdown-item {{ app()->getLocale() === 'id' ? 'active' : '' }}" href="#" onclick="switchLanguageSidebar('id')">
|
||||||
<img src="/img/flags/id.png" class="flex-shrink-0 me-2" width="20" alt="Indonesia">
|
<img src="/img/flags/id.png" class="flex-shrink-0 me-2" width="20" alt="Indonesia">
|
||||||
{{ __('languages.id') }}
|
{{ __('languages.id') }}
|
||||||
</a>
|
</a>
|
||||||
</li>
|
</li>
|
||||||
|
|
||||||
</ul>
|
</ul>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
|
<script>
|
||||||
|
function switchLanguageSidebar(locale) {
|
||||||
|
// Store language in session via AJAX
|
||||||
|
fetch('/locale/switch', {
|
||||||
|
method: 'POST',
|
||||||
|
headers: {
|
||||||
|
'Content-Type': 'application/json',
|
||||||
|
'X-CSRF-TOKEN': document.querySelector('meta[name="csrf-token"]').getAttribute('content')
|
||||||
|
},
|
||||||
|
body: JSON.stringify({
|
||||||
|
locale: locale
|
||||||
|
})
|
||||||
|
})
|
||||||
|
.then(response => response.json())
|
||||||
|
.then(data => {
|
||||||
|
if (data.success) {
|
||||||
|
// Reload page to reflect changes
|
||||||
|
window.location.reload();
|
||||||
|
}
|
||||||
|
})
|
||||||
|
.catch(error => console.error('Error switching language:', error));
|
||||||
|
}
|
||||||
|
</script>
|
||||||
|
|
|
||||||
|
|
@ -1,20 +1,20 @@
|
||||||
<!-- Country selector visible on screens > 768px wide (md breakpoint) -->
|
<!-- Country selector visible on screens > 768px wide (md breakpoint) -->
|
||||||
<div class="dropdown d-none d-md-block nav">
|
<div class="dropdown d-none d-md-block nav">
|
||||||
<a class="nav-link dropdown-toggle py-1 px-0" href="#" data-bs-toggle="dropdown" aria-haspopup="true" aria-expanded="false" aria-label="{{ __('messages.Country select') }}: USA">
|
<a class="nav-link dropdown-toggle py-1 px-0" href="#" data-bs-toggle="dropdown" aria-haspopup="true" aria-expanded="false" aria-label="{{ __('messages.Country select') }}: {{ app()->getLocale() === 'en' ? 'USA' : 'Indonesia' }}">
|
||||||
<div class="ratio ratio-1x1" style="width: 20px">
|
<div class="ratio ratio-1x1" style="width: 20px">
|
||||||
<img src="/img/flags/en-us.png" alt="USA">
|
<img src="/img/flags/{{ session('locale') === 'en' ? 'en-us' : 'id' }}.png" alt="{{ session('locale') === 'en' ? 'USA' : 'Indonesia' }}">
|
||||||
</div>
|
</div>
|
||||||
</a>
|
</a>
|
||||||
<ul class="dropdown-menu fs-sm" style="--cz-dropdown-spacer: .5rem">
|
<ul class="dropdown-menu fs-sm" style="--cz-dropdown-spacer: .5rem">
|
||||||
<li>
|
<li>
|
||||||
<a class="dropdown-item" href="#!">
|
<a class="dropdown-item {{ session('locale') === 'en' ? 'active' : '' }}" href="#" onclick="switchLanguage('en')">
|
||||||
<img src="/img/flags/en-us.png" class="flex-shrink-0 me-2" width="20" alt="United States">
|
<img src="/img/flags/en-us.png" class="flex-shrink-0 me-2" width="20" alt="United States">
|
||||||
{{ __('languages.en') }}
|
{{ __('languages.en') }}
|
||||||
</a>
|
</a>
|
||||||
</li>
|
</li>
|
||||||
|
|
||||||
<li>
|
<li>
|
||||||
<a class="dropdown-item" href="#!">
|
<a class="dropdown-item {{ session('locale') === 'id' ? 'active' : '' }}" href="#" onclick="switchLanguage('id')">
|
||||||
<img src="/img/flags/id.png" class="flex-shrink-0 me-2" width="20" alt="Indonesia">
|
<img src="/img/flags/id.png" class="flex-shrink-0 me-2" width="20" alt="Indonesia">
|
||||||
{{ __('languages.id') }}
|
{{ __('languages.id') }}
|
||||||
</a>
|
</a>
|
||||||
|
|
@ -22,3 +22,27 @@
|
||||||
|
|
||||||
</ul>
|
</ul>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
|
<script>
|
||||||
|
function switchLanguage(locale) {
|
||||||
|
// Store language in session via AJAX
|
||||||
|
fetch('/locale/switch', {
|
||||||
|
method: 'POST',
|
||||||
|
headers: {
|
||||||
|
'Content-Type': 'application/json',
|
||||||
|
'X-CSRF-TOKEN': document.querySelector('meta[name="csrf-token"]').getAttribute('content')
|
||||||
|
},
|
||||||
|
body: JSON.stringify({
|
||||||
|
locale: locale
|
||||||
|
})
|
||||||
|
})
|
||||||
|
.then(response => response.json())
|
||||||
|
.then(data => {
|
||||||
|
if (data.success) {
|
||||||
|
// Reload page to reflect changes
|
||||||
|
window.location.reload();
|
||||||
|
}
|
||||||
|
})
|
||||||
|
.catch(error => console.error('Error switching language:', error));
|
||||||
|
}
|
||||||
|
</script>
|
||||||
|
|
|
||||||
|
|
@ -17,5 +17,5 @@
|
||||||
<meta name="apple-mobile-web-app-capable" content="yes">
|
<meta name="apple-mobile-web-app-capable" content="yes">
|
||||||
<meta name="apple-mobile-web-app-status-bar-style" content="black">
|
<meta name="apple-mobile-web-app-status-bar-style" content="black">
|
||||||
<link rel="manifest" href="/manifest.json">
|
<link rel="manifest" href="/manifest.json">
|
||||||
<link rel="icon" type="image/png" href="/app-icons/icon-32x32.png" sizes="32x32">
|
<link rel="icon" type="image/png" href="{{ asset('logo/logo-app.png') }}" sizes="32x32">
|
||||||
<link rel="apple-touch-icon" href="/app-icons/icon-180x180.png">
|
<link rel="apple-touch-icon" href="{{ asset('app-icons/icon-180x180.png') }}">
|
||||||
|
|
|
||||||
|
|
@ -4,6 +4,7 @@ use App\Http\Controllers\HomeController;
|
||||||
use Illuminate\Support\Facades\Route;
|
use Illuminate\Support\Facades\Route;
|
||||||
use App\Http\Controllers\RoutingController;
|
use App\Http\Controllers\RoutingController;
|
||||||
use App\Http\Controllers\LocationController;
|
use App\Http\Controllers\LocationController;
|
||||||
|
use App\Http\Controllers\LocaleController;
|
||||||
|
|
||||||
Route::group(['prefix' => '/dummy'], function () {
|
Route::group(['prefix' => '/dummy'], function () {
|
||||||
Route::get('', [RoutingController::class, 'index'])->name('root');
|
Route::get('', [RoutingController::class, 'index'])->name('root');
|
||||||
|
|
@ -16,4 +17,7 @@ Route::group(['prefix' => '/dummy'], function () {
|
||||||
// Location selection route
|
// Location selection route
|
||||||
Route::post('/location/select', [LocationController::class, 'select'])->name('location.select');
|
Route::post('/location/select', [LocationController::class, 'select'])->name('location.select');
|
||||||
|
|
||||||
|
// Language switching route
|
||||||
|
Route::post('/locale/switch', [LocaleController::class, 'switch'])->name('locale.switch');
|
||||||
|
|
||||||
Route::get('/', [HomeController::class, 'index'])->name('home');
|
Route::get('/', [HomeController::class, 'index'])->name('home');
|
||||||
Loading…
Reference in New Issue