feat: add "other" button with dynamic link list for additional projects and services
continuous-integration/drone/push Build is passing

This commit is contained in:
martin.fencl
2026-11-10 09:49:46 +01:00
parent 16804546e9
commit 1570f6cfca
3 changed files with 168 additions and 2 deletions
+19
View File
@@ -39,6 +39,25 @@ class Global_conf {
);
// List shown under the "other" button on the home page.
// section => array( array(label, url, note), ... )
// Relative URLs open in the same tab, absolute (https://...) in a new tab.
public $other_links = array(
"projects" => array(
array("Ločenice – Sluneční vrch", "/locenice/", ""),
array("Klabava – rodinný dům", "/klabava/", ""),
array("Kovářova – rodinný dům", "/kovarova/", ""),
),
"services" => array(
array("Valheim map", "https://valheim-mapa.martinfencl.eu/", ""),
array("Dashboard", "https://dashboard.martinfencl.eu/", "Homarr"),
array("Photos", "https://photo.martinfencl.eu/", "Immich"),
array("Cloud", "https://cloud.martinfencl.eu/", "Nextcloud"),
array("Film", "https://film.martinfencl.eu/", "Jellyfin"),
array("BetterShift", "https://bettershift.martinfencl.eu/", "shifts"),
),
);
}
?>
+100
View File
@@ -716,3 +716,103 @@ button:hover {
button:focus {
outline: none;
}
/* "other" – half-size twin of the "about me" button, opens a link list above itself */
#Other_wrap {
position: relative;
display: inline-block;
margin-top: 18px;
}
#Other_btn {
width: 90px;
height: 20px;
padding: 0;
font-size: 10px;
line-height: 1;
border-width: 1px;
box-shadow: 2px 2px 0 #6f619e,
-2px -2px 0 #6f619e,
-2px 2px 0 #6f619e,
2px -2px 0 #6f619e;
}
#Other_btn:hover,
#Other_btn[aria-expanded="true"] {
box-shadow: 10px 2px 0 #6f619e, -10px -2px 0 #6f619e;
}
#Other_list {
display: none;
position: absolute;
bottom: calc(100% + 10px); /* low enough to fully cover the "about me" button while open */
left: 50%;
transform: translateX(-50%);
z-index: 5;
width: 300px;
max-width: calc(100vw - 32px);
box-sizing: border-box;
padding: 15px 20px;
background-color: rgba(0, 0, 0, 0.95);
-webkit-backdrop-filter: blur(6px);
backdrop-filter: blur(6px);
border-radius: 15px;
color: rgb(238, 238, 255);
text-align: left;
font-family: Lucida Console, Lucida Sans Typewriter, monaco, Bitstream Vera Sans Mono, monospace;
font-size: 15px;
line-height: 25px;
}
#Other_list .other-section {
margin-top: 12px;
font-size: 11px;
letter-spacing: .15em;
text-transform: uppercase;
color: #a99fd0;
}
#Other_list .other-section:first-child {
margin-top: 0;
}
#Other_list ul {
list-style: none;
margin: 0;
padding: 0;
}
#Other_list a {
display: flex;
justify-content: space-between;
align-items: baseline;
gap: 10px;
margin: 0 -8px;
padding: 1px 8px;
border-radius: 6px;
transition: background-color 0.2s ease;
}
#Other_list a:hover,
#Other_list a:focus-visible {
background-color: rgba(111, 97, 158, 0.55);
outline: none;
}
#Other_list .other-note {
font-size: 12px;
color: rgba(238, 238, 255, 0.55);
}
#Other_list_arrow {
position: absolute;
left: 50%;
bottom: -7px;
width: 0;
height: 0;
margin-left: -8px;
border-left: 8px solid transparent;
border-right: 8px solid transparent;
border-top: 7px solid rgba(0, 0, 0, 0.95);
}
+47
View File
@@ -104,6 +104,27 @@
<button class="name noselect">about me</button>
</form>
</table>
<div id="Other_wrap">
<button type="button" id="Other_btn" class="noselect" aria-expanded="false" aria-controls="Other_list">other</button>
<div id="Other_list">
<?php foreach ($global->other_links as $section => $links): ?>
<div class="other-section"><?php echo htmlspecialchars($section); ?></div>
<ul>
<?php foreach ($links as $link):
$is_external = strpos($link[1], 'http') === 0; ?>
<li><a href="<?php echo htmlspecialchars($link[1]); ?>"<?php if ($is_external) echo ' target="_blank" rel="noopener"'; ?>>
<span><?php echo htmlspecialchars($link[0]); ?></span>
<?php if ($link[2] !== ''): ?>
<span class="other-note"><?php echo htmlspecialchars($link[2]); ?></span>
<?php endif; ?>
</a></li>
<?php endforeach; ?>
</ul>
<?php endforeach; ?>
<div id="Other_list_arrow"></div>
</div>
</div>
</td>
</tr>
</table>
@@ -136,6 +157,32 @@
$("#Bank_info_ext").stop().fadeOut(300);
});
var $otherBtn = $("#Other_btn");
var $otherList = $("#Other_list");
function setOtherOpen(open) {
if (open === ($otherBtn.attr("aria-expanded") === "true")) return;
$otherBtn.attr("aria-expanded", open ? "true" : "false");
if (open) {
$otherList.stop(true, true).fadeIn(200);
} else {
$otherList.stop(true, true).fadeOut(200);
}
}
$otherBtn.on("click", function () {
setOtherOpen($otherBtn.attr("aria-expanded") !== "true");
});
// close on click outside or Escape
$(document).on("click", function (e) {
if (!$(e.target).closest("#Other_wrap").length) setOtherOpen(false);
});
$(document).on("keydown", function (e) {
if (e.key === "Escape" || e.keyCode === 27) setOtherOpen(false);
});
function copyNumber() {
copyToClipboard('<?php echo $global->phone_list[0]; ?>');
alert("phone copied to clipboard")