Compare commits

..

2 Commits

Author SHA1 Message Date
Frederico @ VilaRosa02
42206afc88 BUG: the navbar works well in light-theme 2025-09-17 18:12:28 +00:00
Frederico @ VilaRosa02
039d586d7b IMPROVEMENT: replace header with Bootstrap top navbar 2025-09-17 18:02:04 +00:00
3 changed files with 109 additions and 24 deletions

View File

@ -1,26 +1,41 @@
<?php // index.php — Simple ChatGPT-like UI in a single PHP file (Bootstrap 5)
require_once __DIR__."/backend.php"; ?>
<!doctype html>
<html lang="en" data-theme="<?= $theme ?>">
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1">
<title>Mini ChatGPT (PHP + Bootstrap)</title>
<title>FMF GPT</title>
<link href="https://cdn.jsdelivr.net/npm/bootstrap@5.3.3/dist/css/bootstrap.min.css" rel="stylesheet">
<link href="/main.css" rel="stylesheet">
</head>
<body>
<div class="container py-4 chat-wrap">
<div class="d-flex align-items-center mb-3 text-white">
<svg xmlns="http://www.w3.org/2000/svg" width="28" height="28" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="me-2"><path d="M12 20h9"/><path d="M16 4h-3a2 2 0 0 0-2 2v14"/><path d="M18 14h-8"/><path d="M7 8h8"/></svg>
<h1 class="h4 m-0">Mini ChatGPT</h1>
<div class="ms-auto">
<button id="resetBtn" class="btn btn-sm btn-outline-light">Reset</button>
</div>
<button id="themeToggle" class="btn btn-sm btn-outline-light ms-2" aria-pressed="false">
<nav class="navbar navbar-expand-lg navbar-dark bg-dark rounded mb-3 px-3">
<a class="navbar-brand" href="#">FMF GPT</a>
<button class="navbar-toggler" type="button" data-bs-toggle="collapse"
data-bs-target="#topNav" aria-controls="topNav"
aria-expanded="false" aria-label="Toggle navigation">
<span class="navbar-toggler-icon"></span>
</button>
<div class="collapse navbar-collapse" id="topNav">
<ul class="navbar-nav me-auto mb-2 mb-lg-0">
<li class="nav-item">
<a class="nav-link active" href="#chat">Chat</a>
</li>
<li class="nav-item">
<a class="nav-link" href="#systemAcc">System</a>
</li>
</ul>
<div class="d-flex">
<button id="resetBtn" class="btn btn-sm btn-outline-light me-2">Reset</button>
<button id="themeToggle" class="btn btn-sm btn-outline-light" aria-pressed="false">
Toggle Theme
</button>
</div>
</div>
</nav>
<div class="accordion mb-3" id="systemAcc">
<div class="accordion-item">
@ -70,7 +85,6 @@ require_once __DIR__."/backend.php"; ?>
</div>
<div class="d-flex gap-2">
<button id="sendBtn" type="submit" class="btn btn-primary">Send</button>
<button id="saveSysBtn" type="button" class="btn btn-outline-secondary">Save System Prompt</button>
</div>
</div>
</form>

View File

@ -13,7 +13,7 @@
html[data-theme="light"] {
/* Light theme (WhatsApp-like) */
--wa-bg: #ece5dd;
--wa-bg: #e9ecef;
--wa-panel: #ffffff;
--wa-incoming: #ffffff; /* assistant (other person) */
--wa-outgoing: #dcf8c6; /* user (me) */
@ -128,3 +128,84 @@ html[data-theme="light"] #themeToggle.btn-outline-light:hover {
background-color: var(--muted);
color: #fff;
}
/* --- Light theme: make the navbar truly light --- */
html[data-theme="light"] .navbar {
background-color: #f8f9fa !important; /* light bg (like .bg-light) */
/* override Bootstrap navbar-dark CSS variables to dark text */
--bs-navbar-color: rgba(0,0,0,.65);
--bs-navbar-hover-color: rgba(0,0,0,.85);
--bs-navbar-active-color: rgba(0,0,0,1);
--bs-navbar-brand-color: rgba(0,0,0,.9);
--bs-navbar-toggler-border-color: rgba(0,0,0,.15);
/* dark “hamburger” icon on light bg */
--bs-navbar-toggler-icon-bg: url("data:image/svg+xml,%3csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 30 30'%3e%3cpath stroke='rgba(0,0,0,0.7)' stroke-linecap='round' stroke-miterlimit='10' stroke-width='2' d='M4 7h22M4 15h22M4 23h22'/%3e%3c/svg%3e");
}
/* Optional: tighten brand + links for light theme (keeps consistency) */
html[data-theme="light"] .navbar .navbar-brand,
html[data-theme="light"] .navbar .nav-link {
color: var(--bs-navbar-color) !important;
}
html[data-theme="light"] .navbar .nav-link.active,
html[data-theme="light"] .navbar .nav-link:focus,
html[data-theme="light"] .navbar .nav-link:hover {
color: var(--bs-navbar-hover-color) !important;
}
/* --- Dark theme fixes for Bootstrap panels (card + accordion) --- */
html:not([data-theme="light"]) .card,
html:not([data-theme="light"]) .accordion,
html:not([data-theme="light"]) .accordion-item {
background-color: var(--wa-panel) !important;
color: var(--wa-text) !important;
border: 1px solid rgba(255,255,255,0.06) !important;
}
/* Accordion header button */
html:not([data-theme="light"]) .accordion-button {
background-color: var(--wa-panel) !important;
color: var(--wa-text) !important;
box-shadow: none !important;
border-bottom: 1px solid rgba(255,255,255,0.06) !important;
}
/* Collapsed state keeps same colors (Bootstrap otherwise goes light) */
html:not([data-theme="light"]) .accordion-button.collapsed {
background-color: var(--wa-panel) !important;
color: var(--wa-text) !important;
border-bottom-color: rgba(255,255,255,0.06) !important;
}
/* Accordion body */
html:not([data-theme="light"]) .accordion-body {
background-color: var(--wa-panel) !important;
color: var(--wa-text) !important;
}
/* The chevron icon (SVG background-image) needs contrast */
html:not([data-theme="light"]) .accordion-button::after {
filter: invert(1) opacity(0.7);
}
/* Inputs inside the card/accordion */
html:not([data-theme="light"]) .form-control {
background-color: var(--wa-incoming) !important;
color: var(--wa-text) !important;
border-color: rgba(255,255,255,0.08) !important;
}
html:not([data-theme="light"]) .form-control::placeholder {
color: var(--wa-muted) !important;
}
html:not([data-theme="light"]) .form-text {
color: var(--wa-muted) !important;
}
/* Outline buttons in dark context */
html:not([data-theme="light"]) .btn-outline-light {
color: var(--wa-text) !important;
border-color: rgba(255,255,255,0.25) !important;
}
html:not([data-theme="light"]) .btn-outline-light:hover {
background-color: rgba(255,255,255,0.12) !important;
}

10
main.js
View File

@ -74,16 +74,6 @@ formEl?.addEventListener('submit', async (e) => {
}
});
// Save system prompt
qs('#saveSysBtn')?.addEventListener('click', async () => {
const message = '';
const system = sysInput ? sysInput.value.trim() : '';
if (!system) return;
// Use a no-op message to persist system prompt? Better: do nothing and let backend save on 'chat'
// Here we just show a toast-like confirmation:
appendAssistantHtml('<em>System prompt saved for next messages.</em>');
});
// Reset chat
resetBtn?.addEventListener('click', async () => {
const res = await post('reset', {});