diff --git a/admin_hospital.php b/admin_hospital.php index fddf64d..4bdd74f 100644 --- a/admin_hospital.php +++ b/admin_hospital.php @@ -98,6 +98,21 @@ qh_page_start( +
+ + +
+
+ + +
diff --git a/assets/css/custom.css b/assets/css/custom.css index 0e3414a..12d8fa6 100644 --- a/assets/css/custom.css +++ b/assets/css/custom.css @@ -1184,7 +1184,7 @@ html[dir="rtl"] .hospital-detail-list dd { top: 0; width: 80mm; margin: 0; - padding: 5mm; + padding: 2mm 5mm; display: block !important; background: white; color: black; @@ -1197,40 +1197,40 @@ html[dir="rtl"] .hospital-detail-list dd { } .pt-header { - font-size: 1.2rem; + font-size: 1rem; font-weight: bold; - margin-bottom: 5px; + margin-bottom: 2px; border-bottom: 1px solid black; - padding-bottom: 5px; + padding-bottom: 2px; } .pt-token-title { - font-size: 0.9rem; - margin-top: 10px; + font-size: 0.8rem; + margin-top: 5px; } .pt-token-number { - font-size: 3.5rem; + font-size: 2.5rem; font-weight: bold; line-height: 1; - margin: 5px 0 10px 0; + margin: 2px 0 5px 0; } .pt-patient-name { - font-size: 1.1rem; + font-size: 0.9rem; font-weight: bold; - margin-bottom: 10px; + margin-bottom: 5px; } .pt-divider { border-top: 1px dashed black; - margin: 10px 0; + margin: 5px 0; } .pt-detail { - font-size: 1rem; + font-size: 0.85rem; text-align: left; - margin-bottom: 5px; + margin-bottom: 2px; display: flex; justify-content: space-between; } @@ -1245,13 +1245,13 @@ html[dir="rtl"] .hospital-detail-list dd { } .pt-datetime { - margin-top: 8px; - font-size: 0.85rem; + margin-top: 4px; + font-size: 0.75rem; } .pt-footer { - font-size: 0.85rem; - margin-top: 10px; + font-size: 0.75rem; + margin-top: 5px; } @page { diff --git a/assets/js/main.js b/assets/js/main.js index 51760ac..9ac5238 100644 --- a/assets/js/main.js +++ b/assets/js/main.js @@ -37,11 +37,19 @@ document.addEventListener('DOMContentLoaded', () => { }); const locale = document.body.dataset.locale || 'en'; + const timeZone = document.body.dataset.timezone || 'UTC'; const liveClock = document.querySelector('.js-live-clock'); if (liveClock) { const renderClock = () => { const now = new Date(); - liveClock.textContent = now.toLocaleTimeString(locale === 'ar' ? 'ar-SA' : 'en-US', { hour: '2-digit', minute: '2-digit' }); + const opts = { hour: '2-digit', minute: '2-digit' }; + if (timeZone) opts.timeZone = timeZone; + try { + liveClock.textContent = now.toLocaleTimeString(locale === 'ar' ? 'ar-SA' : 'en-US', opts); + } catch (e) { + opts.timeZone = undefined; + liveClock.textContent = now.toLocaleTimeString(locale === 'ar' ? 'ar-SA' : 'en-US', opts); + } }; renderClock(); window.setInterval(renderClock, 1000 * 30); diff --git a/queue_bootstrap.php b/queue_bootstrap.php index 3347a74..32d911d 100644 --- a/queue_bootstrap.php +++ b/queue_bootstrap.php @@ -17,6 +17,17 @@ function qh_boot(): void qh_ensure_schema(); qh_seed_demo_data(); qh_seed_hospital_profile(); + + $profile = qh_fetch_hospital_profile(); + $timezone = $profile['timezone'] ?? 'UTC'; + if ($timezone) { + date_default_timezone_set($timezone); + try { + $offset = (new DateTime('now', new DateTimeZone($timezone)))->format('P'); + db()->exec("SET time_zone = " . db()->quote($offset)); + } catch (\Throwable $e) {} + } + $booted = true; } @@ -81,6 +92,8 @@ SQL; db()->exec($profileSql); try { db()->exec("ALTER TABLE hospital_profile_settings ADD COLUMN news_ticker_en VARCHAR(1000) DEFAULT NULL"); } catch (\Throwable $e) {} try { db()->exec("ALTER TABLE hospital_profile_settings ADD COLUMN news_ticker_ar VARCHAR(1000) DEFAULT NULL"); } catch (\Throwable $e) {} + try { db()->exec("ALTER TABLE hospital_profile_settings ADD COLUMN timezone VARCHAR(100) DEFAULT 'UTC'"); } catch (\Throwable $e) {} + try { db()->exec("ALTER TABLE hospital_profile_settings ADD COLUMN default_language VARCHAR(10) DEFAULT 'en'"); } catch (\Throwable $e) {} } function qh_seed_demo_data(): void @@ -230,8 +243,14 @@ function qh_locale(): string $_SESSION['qh_lang'] = $requested; } - $sessionLocale = strtolower(trim((string) ($_SESSION['qh_lang'] ?? 'en'))); - $locale = in_array($sessionLocale, ['en', 'ar'], true) ? $sessionLocale : 'en'; + $sessionLocale = strtolower(trim((string) ($_SESSION['qh_lang'] ?? ''))); + if (in_array($sessionLocale, ['en', 'ar'], true)) { + $locale = $sessionLocale; + } else { + $profile = qh_fetch_hospital_profile(); + $defaultLang = strtolower(trim((string) ($profile['default_language'] ?? 'en'))); + $locale = in_array($defaultLang, ['en', 'ar'], true) ? $defaultLang : 'en'; + } return $locale; } @@ -551,7 +570,9 @@ function qh_page_start(string $activePage, string $pageTitle, string $metaDescri echo ' '; echo ' '; echo ''; - echo ''; + $profile = qh_fetch_hospital_profile(); + $timezone = qh_h($profile['timezone'] ?? 'UTC'); + echo ''; if ($activePage !== 'display') { qh_render_nav($activePage); } @@ -1115,6 +1136,10 @@ function qh_admin_handle_request(): void $workingHoursAr = trim((string) ($_POST['working_hours_ar'] ?? '')); $newsTickerEn = trim((string) ($_POST['news_ticker_en'] ?? '')); $newsTickerAr = trim((string) ($_POST['news_ticker_ar'] ?? '')); + $timezone = trim((string) ($_POST['timezone'] ?? '')); + if ($timezone === '' || !in_array($timezone, timezone_identifiers_list(), true)) $timezone = 'UTC'; + $defaultLanguage = trim((string) ($_POST['default_language'] ?? 'en')); + if (!in_array($defaultLanguage, ['en', 'ar'], true)) $defaultLanguage = 'en'; $profile = qh_fetch_hospital_profile(); $logoUrl = $profile['logo_url'] ?? ''; $faviconUrl = $profile['favicon_url'] ?? ''; @@ -1165,7 +1190,9 @@ function qh_admin_handle_request(): void primary_color = :primary_color, secondary_color = :secondary_color, news_ticker_en = :news_ticker_en, - news_ticker_ar = :news_ticker_ar + news_ticker_ar = :news_ticker_ar, + timezone = :timezone, + default_language = :default_language WHERE id = 1" ); $stmt->execute([ @@ -1187,6 +1214,8 @@ function qh_admin_handle_request(): void 'secondary_color' => $secondaryColor, 'news_ticker_en' => $newsTickerEn, 'news_ticker_ar' => $newsTickerAr, + 'timezone' => $timezone, + 'default_language' => $defaultLanguage, ]); qh_set_flash('success', qh_t('Hospital profile updated successfully.', 'تم تحديث ملف المستشفى بنجاح.')); }