diff --git a/config/bootstrap.php b/config/bootstrap.php index 3998f86..372109a 100644 --- a/config/bootstrap.php +++ b/config/bootstrap.php @@ -46,7 +46,7 @@ function handle_setup_exception(SetupException $e){ case 'table_contents': // Recoverable error. // Redirect to setup if we aren't already headed there. - global $config; + $config = ConfigModel::load(); $currentPath = trim(parse_url($_SERVER['REQUEST_URI'], PHP_URL_PATH), '/'); if (strpos($currentPath, 'setup') === false) { diff --git a/public/css/tkr.css b/public/css/tkr.css index aa9e619..76da718 100644 --- a/public/css/tkr.css +++ b/public/css/tkr.css @@ -203,12 +203,108 @@ label.description { line-height: 1.2; } +.navbar { + overflow: hidden; + background: var(--color-bg-white); +} + +.navbar a { + float: left; + font-size: 16px; + color: var(--color-text-secondary); + text-align: center; + padding: 14px 16px; + text-decoration: none; +} + +.navbar a:hover { + background: var(--color-hover-light); + color: var(--color-primary-dark); +} + +.navbar a:focus { + outline: none; + background: var(--color-hover-light); + box-shadow: 0 0 0 2px var(--shadow-primary); +} + +/* + Dropdown menu styling + https://www.w3schools.com/howto/howto_css_dropdown.asp +*/ + +.dropdown { + float: left; + overflow: hidden; +} + +.dropdown .dropbtn { + font-size: 16px; + border: none; + border-radius: 0px; /* overrides default button corner style */ + outline: none; + color: var(--color-text-secondary); + padding: 14px 16px; + background-color: inherit; + font-family: inherit; + margin: 0; +} + +/* Add a downward-facing caret after the button label */ +.dropdown .dropbtn::after { + content: " ▼"; + font-size: 0.8em; + margin-left: 4px; +} + +.dropdown:hover .dropbtn { + background: var(--color-hover-light); + color: var(--color-primary-dark) +} + +.dropdown-content { + display: none; + position: absolute; + background-color: var(--color-bg-white); + border: 1px solid var(--color-border-light); + border-radius: 6px; + min-width: 160px; + box-shadow: 0px 8px 16px 0px var(--shadow-primary); + z-index: 1; +} + +.dropdown-content a { + float: none; + color: var(--color-text-primary); + padding: 12px 16px; + text-decoration: none; + display: block; + text-align: left; +} + +.dropdown-content a:hover { + background: var(--color-hover-light); + color: var(--color-primary-dark); +} + +.dropdown-content a:focus { + outline: none; + background: var(--color-hover-light); + box-shadow: 0 0 0 2px var(--shadow-primary); +} + +.dropdown:hover .dropdown-content { + display: block; +} + /* The two common display options for responsive layouts are flex and grid. flex (aka Flexbox) aligns items either horizontally or vertically. grid can align items in two dimensions. - grid also allows more precise positioning of elements, so I'm using that. + grid also allows more precise positioning of elements, so I'm using that + even though I only have one dimension. */ + .home-container { display: grid; } @@ -461,4 +557,16 @@ label.description { .file-info { grid-column: 2; } + + .navbar { + flex-wrap: wrap; + } + + .dropdown-menu { + position: fixed; + left: 1em; + right: 1em; + width: auto; + min-width: auto; + } } \ No newline at end of file diff --git a/public/index.php b/public/index.php index e3c4267..a179f03 100644 --- a/public/index.php +++ b/public/index.php @@ -15,28 +15,13 @@ if (preg_match('/\.php$/', $path)) { include_once(dirname(dirname(__FILE__)) . "/config/bootstrap.php"); load_classes(); -// Initialize core entities -// Defining these as globals isn't great practice, -// but this is a small, single-user app and this data will rarely change. +// initialize the database global $db; -global $config; -global $user; - $db = get_db(); -$config = ConfigModel::load(); -$user = UserModel::load(); - -// Remove the base path from the URL -if (strpos($path, $config->basePath) === 0) { - $path = substr($path, strlen($config->basePath)); -} - -// strip the trailing slash from the resulting route -$path = trim($path, '/'); // Make sure the initial setup is complete // unless we're already heading to setup -if (!($path === 'setup')){ +if (!(preg_match('/setup$/', $path))) { try { confirm_setup(); } catch (SetupException $e) { @@ -48,11 +33,28 @@ if (!($path === 'setup')){ // Everything's loaded and setup is confirmed. // Let's start ticking. +// Initialize core entities +// Defining these as globals isn't great practice, +// but this is a small, single-user app and this data will rarely change. +global $config; +global $user; + +$config = ConfigModel::load(); +$user = UserModel::load(); + // Start a session and generate a CSRF Token // if there isn't already an active session Session::start(); Session::generateCsrfToken(); +// Remove the base path from the URL +if (strpos($path, $config->basePath) === 0) { + $path = substr($path, strlen($config->basePath)); +} + +// strip the trailing slash from the resulting route +$path = trim($path, '/'); + // if this is a POST and we aren't in setup, // make sure there's a valid session // if not, redirect to /login or die as appropriate diff --git a/templates/partials/navbar.php b/templates/partials/navbar.php index ec0d92b..1497d1a 100644 --- a/templates/partials/navbar.php +++ b/templates/partials/navbar.php @@ -1,14 +1,25 @@ + \ No newline at end of file