X-Git-Url: https://git.draconx.ca/gitweb/homepage.git/blobdiff_plain/5aa756ee68dc2134b6acac8a66af2f1c14521721..e7306bc0bbfea36e6414684b00ad4ef1c7269aed:/content/style.scss diff --git a/content/style.scss b/content/style.scss index 22df5d9..dc306d7 100644 --- a/content/style.scss +++ b/content/style.scss @@ -1,7 +1,7 @@ /* * Nick's web site: default stylesheet * - * Copyright © 2018-2020 Nick Bowler + * Copyright © 2018-2021 Nick Bowler * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -118,6 +118,7 @@ td, th { thead>tr, tbody>tr { border: solid $ruledefaultcolour; } th, thead>tr { border-bottom: 1px solid $rulestrongcolour; } +tbody+tbody { border-bottom: 1px solid $ruledefaultcolour; } *>table, *>th { border: none; } thead>tr { border-width: 1px; } tbody>tr { border-width: 0 1px; } @@ -137,13 +138,47 @@ table.cc { } } -$sortcols: name, date, size; -@each $col in $sortcols { - #filelist-#{$col}-sort { +// CSS rules for stortable clicky table headers: Update the display of +// the /table based on the current state. Each column has its own set +// nearly-identical rules, only the class names differ. +// +// The clickytables.xsl stylesheet generates two inputs for each column. +// These inputs are siblings of the table and all precede it in document +// order. Moreover, the inputs for a column are ordered with respect to +// each other, in this sequence: +// +// input.clicky-NAME -- checked iff NAME is selected for sorting. +// input.clicky-NAME-rev -- checked to select reverse order. +// +// One of the column selection inputs will have a 'checked' attribute to +// indicate the default order. This input is always first in document +// order. No other inputs begin checked. +// +// The table itself consists of a thead (where the header labels are +// located) and two tbody elements. The bulk of these rules relate +// to updating the headers to visually indicate the current state. +// +// A sortable column's th element has the .clicky-NAME class, matching +// its corresponding inputs, and has two label children. The first label +// is visible only when the column is unselected, and is linked to the +// .clicky-NAME input to activate that column. The second label is visible +// only on the selected column and is linked to the .clicky-NAME-rev input +// to toggle the reverse order. +// +// For the table body, the first tbody contains the default ordering +// and is not styled by these rules (except to hide it when alternate +// orderings are selected). The second tbody contains rows for all +// alternate orderings, and is revealed by these rules. When revealed, +// rows with the NAMEfwd or NAMErev class (for the forward and reverse +// orderings, respectively) are shown and other rows are hidden. + +$clickynames: name, date, size; +@each $col in $clickynames { + input.clicky-#{$col} { &:checked { - & ~ table.filelist { - /* Update table header state */ - th.#{$col} { + &~table { + // Update table header state + & th.clicky-#{$col} { label~label { display: -moz-inline-box !important; display: inline-block !important; @@ -151,60 +186,110 @@ $sortcols: name, date, size; label { display: none; } } - /* Show only appropriate items from the sort body (forward) */ - tbody+tbody>tr.#{$col} { display: table-row; } - tbody+tbody>tr { display: none; } + // Show only appropriate items from the sort body (forward) + &>tbody+tbody>tr.#{$col}fwd { display: table-row; } + &>tbody+tbody>tr { display: none; } + + // Unhide sort body + &>tbody { + &+tbody { display: table-row-group !important; } + display: none; + } } - & ~ #filelist-#{$col}-rev:checked ~ table.filelist { - /* Show only appropriate items from sort body (reversed) */ - tbody+tbody>tr.#{$col}rev { display: table-row; } - tbody+tbody>tr { display: none; } + // reverse state for selected sort column + &~input.clicky-#{$col}-rev { + &:checked ~ table { + // Show only appropriate items from sort body (reversed) + &>tbody+tbody>tr.#{$col}rev { display: table-row; } + &>tbody+tbody>tr { display: none; } + + // Unhide sort body + &>tbody { + &+tbody { display: table-row-group !important; } + display: none; + } + } + + // Unhide to allow keyboard navigation to this input + display: block !important; } + } - /* Unhide associated checkbox for keyboard navigation */ - & ~ #filelist-#{$col}-rev { display: block !important; } + // If default input element is the only one selected, match it to + // return to default view (overriding the changes above). It is + // always the first input element among all the sibling elements. + // This seems to interoperate better than using the [checked] or + // :first-of-type selectors. + @at-root &:first-child, :not(input)+& { + &:checked~table>tbody { + &+tbody { display: none !important; } + display: table-row-group; + } } - &:focus ~ table.filelist th>label~label>span { - border: 1px dotted; - padding: 0; + &:focus ~ table th.clicky-#{$col}>label~label>span { + border-color: $foregroundcolour; } + // Unhide to allow keyboard navigation display: block !important; + pointer-events: none; position: absolute; - z-index: -1; opacity: 0; + z-index: -1; } - #filelist-#{$col}-rev { - &:checked ~ table.filelist { - /* Update table header state */ - th.#{$col} { + input.clicky-#{$col}-rev { + &:checked ~ table { + // Update table header state + & th.clicky-#{$col} { img+img { display: -moz-inline-box !important; - display: inline !important; + display: inline-block !important; } img { display: none; } } } - &:focus ~ table.filelist th>label~label>img { - border: 1px dotted; - padding: 0; + &:focus ~ table th.clicky-#{$col}>label~label>img { + border-color: $foregroundcolour; } + pointer-events: none; position: absolute; - z-index: -2; opacity: 0; + z-index: -2; } -} -/* Enable the sorted tables only when non-default option is selected */ -#filelist-name-rev, #filelist-date-sort, #filelist-size-sort { - &:checked~table.filelist>tbody { - &+tbody { display: table-row-group !important; } - display: none; + th.clicky-#{$col}>label { + &, &>* { + white-space: nowrap; + vertical-align: middle; + display: -moz-inline-box; + display: inline-block; + cursor: pointer; + } + + &>* { border: 1px dotted transparent; } + + // Expand the first label a bit so the table (hopefully) + // does not reshape as columns are selected. + &:first-child { + margin-right: 1.75em; + padding-right: 2px; + } + + &:active { color: $linkactivecolour; } + &:first-child:active>span, &~label:active>img { + border-color: $linkactivecolour; + } + + img { + margin-left: 0.25em; + width: 1.5em; + height: auto; + } } } @@ -214,21 +299,7 @@ table.filelist { width: 0; } - th>label>* { padding: 1px; } - th>label, th>label>* { - white-space: nowrap; - vertical-align: middle; - display: -moz-inline-box; - display: inline-block; - cursor: pointer; - } - th img { margin-left: 0.5ex; } - - tbody+tbody { - border-bottom: solid 1px $ruledefaultcolour; - } - - img { + tbody img { display: block; height: 1.5em; width: auto;