css cleanup.

This commit is contained in:
Greg Sarjeant 2025-06-06 09:03:09 -04:00
parent fb69ca4470
commit 04e813f32c
7 changed files with 313 additions and 112 deletions

View File

@ -12,6 +12,122 @@ a {
font-weight: bold; font-weight: bold;
} }
legend {
background-color: white;
padding: 6px 12px;
border-radius: 4px;
font-weight: 600;
color: #374151;
border: 1px solid #d1d5db;
}
fieldset {
border: 2px solid #e5e7eb;
border-radius: 6px;
padding: 16px;
margin-bottom: 16px;
background-color: #fefefe;
}
/* Grid layout for emoji fieldsets */
fieldset.emoji-group {
display: grid;
grid-template-columns: repeat(auto-fill, minmax(2em, 1fr));
gap: 0.3em;
}
input[type="text"],
input[type="number"],
input[type="password"],
textarea,
select {
width: 100%;
padding: 10px 12px;
border: 1px solid #d1d5db;
border-radius: 6px;
font-family: inherit;
font-size: 1em;
resize: none;
transition: border-color 0.2s ease;
box-sizing: border-box;
}
input[type="text"]:focus,
input[type="number"]:focus,
input[type="password"]:focus,
textarea:focus,
select:focus {
outline: none;
border-color: #4299e1;
box-shadow: 0 0 0 2px rgba(66, 153, 225, 0.1);
}
input[type="file"] {
width: 100%;
padding: 10px;
border: 2px dashed #cbd5e0;
border-radius: 6px;
background-color: #f8fafc;
cursor: pointer;
font-size: 14px;
transition: all 0.3s ease;
box-sizing: border-box;
}
input[type="file"]:hover {
border-color: #4299e1;
background-color: #ebf8ff;
}
input[type="file"]:focus {
outline: none;
border-color: #4299e1;
box-shadow: 0 0 0 3px rgba(66, 153, 225, 0.1);
}
/* Submit buttons */
/* Stop deleting this block */
input[type="submit"],
button[type="submit"] {
padding: 10px 20px;
border: 1px solid #4299e1;
border-radius: 6px;
background-color: #f0f9ff;
color: #1e40af;
font-size: 14px;
font-weight: 600;
cursor: pointer;
transition: all 0.2s ease;
box-sizing: border-box;
}
input[type="submit"]:hover,
button[type="submit"]:hover {
background-color: #dbeafe;
border-color: #3182ce;
}
input[type="submit"]:focus,
button[type="submit"]:focus {
outline: none;
border-color: #2563eb;
box-shadow: 0 0 0 2px rgba(66, 153, 225, 0.1);
}
input[type="submit"]:active,
button[type="submit"]:active {
background-color: #bfdbfe;
}
label {
font-weight: 600;
color: #374151;
text-align: left;
padding-top: 0;
margin-bottom: 3px;
line-height: 1.2;
}
/* /*
The two common display options for responsive layouts are flex and grid. The two common display options for responsive layouts are flex and grid.
flex (aka Flexbox) aligns items either horizontally or vertically. flex (aka Flexbox) aligns items either horizontally or vertically.
@ -22,17 +138,14 @@ a {
display: grid; display: grid;
} }
/* .home-sidebar{
Responsive layout - adjusts from 1 to 2 columns based on screen width padding-bottom: 1em;
min-width makes the mobile (stacked) view the default }
600px covers most mobile devices in portrait mode
Once the width exceeds that (e.g. desktops), it will convert to horizontal alignment .site-description {
*/ font-size: 1.2rem;
@media (min-width: 600px) { color: #333;
.home-container { margin-bottom: 0.5rem;
grid-template-columns: 1fr 2fr;
grid-gap: 2em;
}
} }
.profile-row { .profile-row {
@ -48,19 +161,6 @@ a {
gap: 0.5em; gap: 0.5em;
} }
.tick-form textarea {
width: 100%;
box-sizing: border-box;
resize: none;
padding: 0.5em;
font-family: inherit;
font-size: 1em;
}
.tick-form button {
align-self: flex-end;
}
.mood-bar { .mood-bar {
display: flex; display: flex;
width: 100%; width: 100%;
@ -69,25 +169,90 @@ a {
gap: 0.5em; gap: 0.5em;
} }
.admin-bar { .upload-container {
display: flex; background: white;
border-radius: 8px;
padding: 20px;
box-shadow: 0 4px 6px rgba(0, 0, 0, 0.1);
}
.fieldset-items {
margin-bottom: 14px;
display: grid;
grid-template-columns: 1fr;
gap: 6px;
align-items: start;
}
.file-input-wrapper {
position: relative;
width: 100%; width: 100%;
justify-content: space-between;
align-items: center;
box-sizing: border-box;
padding-top: 1em;
gap: 0.5em;
} }
.admin-right { .file-info {
display: flex; background-color: #f0f9ff;
align-items: center; border: 1px solid #bae6fd;
gap: 0.5em; border-radius: 4px;
padding: 8px;
margin-top: 8px;
font-size: 13px;
color: #0369a1;
grid-column: 1;
} }
.admin-bar a, .upload-btn {
.admin-bar span { background-color: #4299e1;
white-space: nowrap; color: white;
border: none;
padding: 10px 20px;
border-radius: 6px;
font-size: 15px;
font-weight: 600;
cursor: pointer;
width: 100%;
transition: background-color 0.3s ease;
margin-top: 12px;
}
.upload-btn:hover {
background-color: #3182ce;
}
.upload-btn:active {
background-color: #2c5282;
}
.upload-btn:focus {
outline: none;
box-shadow: 0 0 0 3px rgba(66, 153, 225, 0.3);
}
.security-info {
background-color: #fef3c7;
border: 1px solid #f59e0b;
border-radius: 4px;
padding: 12px;
margin-bottom: 16px;
}
.security-info h3 {
color: #92400e;
margin: 0 0 6px 0;
font-size: 15px;
}
.security-info ul {
color: #92400e;
margin: 0;
padding-left: 18px;
}
.security-info li {
margin-bottom: 2px;
}
.required {
color: #dc2626;
} }
.tick { .tick {
@ -105,33 +270,6 @@ a {
.pagination a { margin: 0 5px; text-decoration: none; } .pagination a { margin: 0 5px; text-decoration: none; }
.emoji-tabs {
display: flex;
gap: 0.5em;
margin-bottom: 0.5em;
}
.emoji-tab-button {
text-decoration: none;
font-size: 1.2em;
padding: 0.2em 0.5em;
background: #eee;
border-radius: 0.3em;
}
.emoji-tab-content {
display: grid;
grid-template-columns: repeat(auto-fill, minmax(2em, 1fr));
gap: 0.3em;
margin-bottom: 1em;
}
.emoji-option {
text-align: center;
display: block;
cursor: pointer;
}
.emoji-option input { .emoji-option input {
display: none; display: none;
} }
@ -148,14 +286,39 @@ a {
outline: 2px solid #339; outline: 2px solid #339;
} }
#timezones { /*
max-height: 300px; Responsive layout - adjusts from 1 to 2 columns based on screen width
overflow-y: auto; - min-width makes the mobile (stacked) view the default
border: 1px solid #ccc; - 600px covers most mobile devices in portrait mode
padding: 1em; - Once the width exceeds that (e.g. desktops), it will convert to horizontal alignment
} */
@media (min-width: 600px) {
.home-container {
grid-template-columns: 1fr 2fr;
grid-gap: 2em;
}
.timezone-option { .fieldset-items {
display: block; margin-bottom: 16px;
margin-bottom: 0.5em; display: grid;
grid-template-columns: 200px 1fr;
gap: 16px;
align-items: start;
}
label {
text-align: right;
padding-top: 10px; /* Match input padding */
margin-bottom: 0;
}
.file-info {
grid-column: 2; /* Align with input column */
}
.form-row .fieldset-items {
grid-template-columns: 200px 1fr;
gap: 16px;
margin-bottom: 16px;
}
} }

View File

@ -5,9 +5,6 @@ class HomeView {
?> ?>
<section id="ticks" class="home-ticks"> <section id="ticks" class="home-ticks">
<div class="home-ticks-header">
<h2><?= $siteDescription ?></h2>
</div>
<div class="home-ticks-list"> <div class="home-ticks-list">
<?php foreach ($ticks as $tick): ?> <?php foreach ($ticks as $tick): ?>
<article class="tick"> <article class="tick">

View File

@ -1,26 +1,26 @@
<?php <?php
class MoodView { class MoodView {
private function render_emoji_tabs(array $emojiGroups, string $currentMood): string { private function render_emoji_groups(array $emojiGroups, string $currentMood): string {
$selected_emoji = $currentMood; //user->mood; $selected_emoji = $currentMood; //user->mood;
ob_start(); ob_start();
?> ?>
<?php foreach ($emojiGroups as $group => $emojis): ?> <?php foreach ($emojiGroups as $group => $emojis): ?>
<fieldset id="<?= htmlspecialchars($group) ?>" class="emoji-tab-content"> <fieldset id="<?= htmlspecialchars($group) ?>" class="emoji-group">
<legend><?= ucfirst($group) ?></legend> <legend><?= ucfirst($group) ?></legend>
<?php foreach ($emojis as [$emoji, $description]): ?> <?php foreach ($emojis as [$emoji, $description]): ?>
<label class="emoji-option"> <label class="emoji-option">
<input <input
type="radio" type="radio"
name="mood" name="mood"
value="<?= htmlspecialchars($emoji) ?>" value="<?= htmlspecialchars($emoji) ?>"
aria-label="<?=htmlspecialchars($description ?? 'emoji') ?>" aria-label="<?=htmlspecialchars($description ?? 'emoji') ?>"
<?= $emoji === $selected_emoji ? 'checked' : '' ?> <?= $emoji === $selected_emoji ? 'checked' : '' ?>
> >
<span><?= htmlspecialchars($emoji) ?></span> <span><?= htmlspecialchars($emoji) ?></span>
</label> </label>
<?php endforeach; ?> <?php endforeach; ?>
</fieldset> </fieldset>
<?php endforeach; <?php endforeach;
@ -30,9 +30,9 @@ class MoodView {
function render_mood_picker(array $emojiGroups, string $currentMood): string { function render_mood_picker(array $emojiGroups, string $currentMood): string {
ob_start(); ob_start();
?> ?>
<form method="post" class="emoji-picker-form"> <form method="post" class="emoji-form">
<input type="hidden" name="csrf_token" value="<?= htmlspecialchars($_SESSION['csrf_token']) ?>"> <input type="hidden" name="csrf_token" value="<?= htmlspecialchars($_SESSION['csrf_token']) ?>">
<?= $this->render_emoji_tabs($emojiGroups, $currentMood) ?> <?= $this->render_emoji_groups($emojiGroups, $currentMood) ?>
<button type="submit">Set the mood</button> <button type="submit">Set the mood</button>
</form> </form>
<?php <?php

View File

@ -12,27 +12,68 @@
<div> <div>
<form method="post"> <form method="post">
<input type="hidden" name="csrf_token" value="<?= htmlspecialchars($_SESSION['csrf_token']) ?>"> <input type="hidden" name="csrf_token" value="<?= htmlspecialchars($_SESSION['csrf_token']) ?>">
<fieldset id="user_settings" class="admin-settings-group"> <fieldset>
<legend>User settings</legend> <legend>User settings</legend>
<label class="admin-option">Username: <input type="text" name="username" value="<?= $user->username ?>" required></label><br> <div class="fieldset-items">
<label class="admin-option">Display name: <input type="text" name="display_name" value="<?= $user->displayName ?>" required></label><br> <label>Username <span class=required></span></label>
<label class="admin-option">About: <input type="text" name="about" value="<?= $user->about ?>"></label><br> <input type="text"
<label class="admin-option">Website: <input type="text" name="website" value="<?= $user->website ?>"></label><br> name="username"
value="<?= $user->username ?>"
required>
<label>Display name <span class=required></span></label>
<input type="text"
name="display_name"
value="<?= $user->displayName ?>"
required>
<label>About </label>
<input type="text"
name="about"
value="<?= $user->about ?>">
<label>Website </label>
<input type="text"
name="website"
value="<?= $user->website ?>">
</div>
</fieldset> </fieldset>
<fieldset id="site_settings" class="admin-settings-group"> <fieldset>
<legend>Site settings</legend> <legend>Site settings</legend>
<label class="admin-option">Title: <input type="text" name="site_title" value="<?= $config->siteTitle ?>" required></label><br> <div class="fieldset-items">
<label class="admin-option">Description: <input type="text" name="site_description" value="<?= $config->siteDescription ?>"></label><br> <label>Title <span class=required></span></label>
<label class="admin-option">Base URL: <input type="text" name="base_url" value="<?= $config->baseUrl ?>" required></label><br> <input type="text"
<label class="admin-option">Base path: <input type="text" name="base_path" value="<?= $config->basePath ?>" required></label><br> name="site_title"
<label class="admin-option">Items per page (max 50): <input type="number" name="items_per_page" value="<?= $config->itemsPerPage ?>" min="1" max="50" required></label><br> value="<?= $config->siteTitle ?>"
required>
<label>Description <span class=required></span></label>
<input type="text"
name="site_description"
value="<?= $config->siteDescription ?>">
<label>Base URL </label>
<input type="text"
name="base_url"
value="<?= $config->baseUrl ?>"
required>
<label>Base path <span class=required></span></label>
<input type="text"
name="base_path"
value="<?= $config->basePath ?>"
required>
<label>Items per page (max 50) <span class=required></span></label>
<input type="number"
name="items_per_page"
value="<?= $config->itemsPerPage ?>" min="1" max="50"
required>
</div>
</fieldset> </fieldset>
<fieldset id="change_password" class="admin-settings-group"> <fieldset>
<legend>Change password</legend> <legend>Change password</legend>
<label class="admin-option">New password: <input type="password" name="password"></label><br> <div class="fieldset-items">
<label class="admin-option">Confirm new password: <input type="password" name="confirm_password"></label><br> <label>New password: </label>
<input type="password" name="password">
<label>Confirm new password: </label>
<input type="password" name="confirm_password">
</div>
</fieldset> </fieldset>
<button type="submit">Save Settings</button> <button type="submit" class="submit-btn">Save Settings</button>
</form> </form>
</div> </div>
</body> </body>

View File

@ -26,7 +26,7 @@ echo '<?xml version="1.0" encoding="UTF-8"?>' . "\n";
?> ?>
<item> <item>
<title><?php echo htmlspecialchars($tick['tick']); ?></title> <title><?php echo htmlspecialchars($tick['tick']); ?></title>
<link><?php echo htmlspecialchars($config->basePath . "tick/$tickPath"); ?></link> <link><?php echo htmlspecialchars($config->baseUrl . $config->basePath . "tick/$tickPath"); ?></link>
<description><?php echo htmlspecialchars($tick['tick']); ?></description> <description><?php echo htmlspecialchars($tick['tick']); ?></description>
<pubDate><?php echo date(DATE_RSS, strtotime($tick['timestamp'])); ?></pubDate> <pubDate><?php echo date(DATE_RSS, strtotime($tick['timestamp'])); ?></pubDate>
<guid><?php echo htmlspecialchars($tickPath); ?></guid> <guid><?php echo htmlspecialchars($tickPath); ?></guid>

View File

@ -12,7 +12,7 @@
<div class="home-container"> <div class="home-container">
<section id="sidebar" class="home-sidebar"> <section id="sidebar" class="home-sidebar">
<div class="home-header"> <div class="home-header">
<h2>Hi, I'm <?= $user->displayName ?></h2> <h2 class="site-description"><?= $config->siteDescription ?></h2>
</div> </div>
<p><?= $user->about ?></p> <p><?= $user->about ?></p>
<p>Website: <?= Util::escape_and_linkify($user->website) ?></p> <p>Website: <?= Util::escape_and_linkify($user->website) ?></p>
@ -30,7 +30,7 @@
<form class="tick-form" method="post"> <form class="tick-form" method="post">
<input type="hidden" name="csrf_token" value="<?= htmlspecialchars($_SESSION['csrf_token']) ?>"> <input type="hidden" name="csrf_token" value="<?= htmlspecialchars($_SESSION['csrf_token']) ?>">
<textarea name="tick" placeholder="What's ticking?" rows="3"></textarea> <textarea name="tick" placeholder="What's ticking?" rows="3"></textarea>
<button type="submit">Tick</button> <button type="submit" class="submit-btn">Tick</button>
</form> </form>
</div> </div>
<?php endif; ?> <?php endif; ?>

View File

@ -16,7 +16,7 @@
<input type="hidden" name="csrf_token" value="<?= htmlspecialchars($csrf_token) ?>"> <input type="hidden" name="csrf_token" value="<?= htmlspecialchars($csrf_token) ?>">
<label>Username: <input type="text" name="username" required></label><br> <label>Username: <input type="text" name="username" required></label><br>
<label>Password: <input type="password" name="password" required></label><br> <label>Password: <input type="password" name="password" required></label><br>
<button type="submit">Login</button> <button type="submit" class="submit-btn">Login</button>
</form> </form>
</body> </body>
</html> </html>