mirror of
https://github.com/paperless-ngx/paperless-ngx.git
synced 2025-04-02 13:45:10 -05:00
265 lines
6.8 KiB
SCSS
265 lines
6.8 KiB
SCSS
@mixin paperless-green {
|
|
// base color e.g. #17541f = hsl(128, 57%, 21%)
|
|
--pngx-primary: 128, 57%;
|
|
--pngx-primary-lightness: 21%;
|
|
}
|
|
|
|
body {
|
|
@include paperless-green;
|
|
--pngx-primary-text-contrast: var(--bs-light);
|
|
|
|
--bs-primary: hsl(var(--pngx-primary), var(--pngx-primary-lightness));
|
|
--bs-border-color: var(--bs-gray-400);
|
|
--pngx-primary-faded: hsl(var(--pngx-primary), calc(var(--pngx-primary-lightness) + 76%));
|
|
--pngx-primary-lighten-30: hsl(var(--pngx-primary), calc(var(--pngx-primary-lightness) + 30%));
|
|
--pngx-primary-darken-5: hsl(var(--pngx-primary), calc(var(--pngx-primary-lightness) - 5%));
|
|
--pngx-primary-darken-15: hsl(var(--pngx-primary), calc(var(--pngx-primary-lightness) - 15%));
|
|
--pngx-primary-darken-18: hsl(var(--pngx-primary), calc(var(--pngx-primary-lightness) - 18%));
|
|
--pngx-primary-darken-27: hsl(var(--pngx-primary), calc(var(--pngx-primary-lightness) - 27%));
|
|
--pngx-bg-alt: #fff;
|
|
--pngx-bg-darker: var(--bs-gray-100);
|
|
--pngx-focus-alpha: 0.3;
|
|
}
|
|
|
|
// Dark text colors allow for maintain contrast with theme color changes
|
|
$text-color-light-bg: #212529;
|
|
$text-color-dark-bg: #abb2bf;
|
|
$text-color-dark-bg-accent: lighten($text-color-dark-bg, 10%);
|
|
// Taken from bootstrap
|
|
$form-check-input-checked-bg-image-dark: url("data:image/svg+xml,<svg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 20 20'><path fill='none' stroke='#{$text-color-light-bg}' stroke-linecap='round' stroke-linejoin='round' stroke-width='3' d='M6 10l3 3l6-6'/></svg>");
|
|
$form-check-radio-checked-bg-image-dark: url("data:image/svg+xml,<svg xmlns='http://www.w3.org/2000/svg' viewBox='-4 -4 8 8'><circle r='2' fill='#{$text-color-light-bg}'/></svg>");
|
|
|
|
.primary-light {
|
|
--pngx-primary-text-contrast: #{$text-color-light-bg} !important;
|
|
|
|
.form-check-input:checked[type=checkbox] {
|
|
background-image: escape-svg($form-check-input-checked-bg-image-dark);
|
|
}
|
|
|
|
.form-check-input:checked[type=radio] {
|
|
background-image: escape-svg($form-check-radio-checked-bg-image-dark);
|
|
}
|
|
|
|
.toast .btn-close {
|
|
filter: none !important;
|
|
}
|
|
}
|
|
|
|
.primary-dark {
|
|
--pngx-primary-text-contrast: #{$text-color-dark-bg} !important;
|
|
}
|
|
|
|
// Dark mode
|
|
@mixin paperless-green-dark-mode {
|
|
--pngx-primary-lightness: 31%;
|
|
}
|
|
|
|
@mixin dark-mode {
|
|
--bs-body-color: #{$text-color-dark-bg};
|
|
--pngx-body-color-accent: #{$text-color-dark-bg-accent};
|
|
--bs-danger: #b71631;
|
|
--bs-danger-rgb: 183, 22, 49;
|
|
--bs-body-bg: #161618;
|
|
--bs-body-bg-rgb: 22, 22, 24;
|
|
--bs-light: #1c1c1f;
|
|
--bs-light-rgb: 28, 28, 31;
|
|
--bs-border-color: #47494f;
|
|
--pngx-bg-darker: #101216;
|
|
--pngx-bg-alt: #242529;
|
|
--pngx-focus-alpha: 0.6;
|
|
--pngx-primary-faded: var(--pngx-primary-darken-15);
|
|
--pngx-primary-text-contrast: var(--bs-body-color);
|
|
|
|
.text-dark, .text-light {
|
|
color: var(--bs-body-color) !important;
|
|
}
|
|
|
|
.btn-primary {
|
|
&:hover, &:focus, &.active, &:active {
|
|
color: var(--bs-body-color) !important;
|
|
}
|
|
}
|
|
|
|
.btn-dark {
|
|
--bs-btn-color: $text-color-dark-bg;
|
|
--bs-btn-bg: var(--pngx-bg-alt);
|
|
--bs-btn-border-color: var(--pngx-bg-alt);
|
|
--bs-btn-hover-bg: var(--bs-light);
|
|
--bs-btn-hover-border-color: var(--pngx-bg-darker);
|
|
--bs-btn-active-bg: var(--pngx-bg-alt);
|
|
}
|
|
|
|
.btn-outline-primary {
|
|
&:hover, &:focus, &.active, &:active {
|
|
color: var(--bs-light) !important;
|
|
}
|
|
}
|
|
|
|
.btn-outline-secondary {
|
|
&:hover, &:focus, &.active, &:active {
|
|
background-color: var(--pngx-bg-darker);
|
|
color: var(--bs-primary);
|
|
}
|
|
}
|
|
|
|
.btn-light {
|
|
color: var(--bs-body-color);
|
|
}
|
|
|
|
.btn .progress {
|
|
background-color: var(--pngx-body-color-accent);
|
|
}
|
|
|
|
.search-form-container {
|
|
input, input:focus {
|
|
color: var(--bs-body-color) !important;
|
|
}
|
|
}
|
|
|
|
.card {
|
|
background-color: var(--bs-body-bg);
|
|
|
|
.card-header {
|
|
background-color: rgba(0, 0, 0, 0.12);
|
|
}
|
|
}
|
|
|
|
.modal-content, .modal-header, .modal-body, .modal-footer {
|
|
background-color: var(--bs-body-bg);
|
|
border-color: var(--bs-border-color);
|
|
}
|
|
|
|
app-tag .badge {
|
|
filter: brightness(.8);
|
|
}
|
|
|
|
.badge.bg-light.border {
|
|
border-color: rgba(0,0,0,0) !important;
|
|
}
|
|
|
|
.document-card .card-body.bg-light {
|
|
background-color: var(--bs-body-bg);
|
|
}
|
|
|
|
.doc-img {
|
|
mix-blend-mode: normal;
|
|
border-radius: 0;
|
|
border-color: var(--bs-border-color);
|
|
filter: invert(10%);
|
|
|
|
&.border-end {
|
|
border-right: none !important;
|
|
}
|
|
}
|
|
|
|
.doc-img.inverted {
|
|
filter: invert(95%) hue-rotate(180deg);
|
|
}
|
|
|
|
.card-selected .doc-img {
|
|
mix-blend-mode: luminosity;
|
|
}
|
|
|
|
.ng-dropdown-panel .ng-dropdown-panel-items .ng-option:hover,
|
|
.ng-dropdown-panel .ng-dropdown-panel-items .ng-option.ng-option-marked {
|
|
background-color: var(--bs-light);
|
|
}
|
|
|
|
.ng-select-multiple .ng-select-container .ng-value-container .ng-value {
|
|
background-color: var(--pngx-bg-alt);
|
|
color: var(--bs-body-color);
|
|
|
|
.ng-value-icon.left {
|
|
border-color: var(--pngx-bg-alt);
|
|
|
|
&:hover {
|
|
background-color: var(--pngx-primary-lighten-30);
|
|
}
|
|
}
|
|
}
|
|
|
|
table {
|
|
.des,
|
|
.asc {
|
|
&::after {
|
|
filter: invert(0.8); /* arrow is a black inline png bkgd image (!) so use filter */
|
|
}
|
|
}
|
|
|
|
&.table-hover > tbody > tr:hover > * {
|
|
background-color: var(--bs-light);
|
|
color: var(--pngx-body-color-accent);
|
|
}
|
|
|
|
}
|
|
|
|
.alert-secondary {
|
|
background-color: var(--bs-light);
|
|
border-color: var(--pngx-bg-darker);
|
|
color: var(--bs-body-color);
|
|
}
|
|
|
|
.alert-primary {
|
|
--bs-alert-color: var(--pngx-primary-text-contrast);
|
|
--bs-alert-bg: var(--pngx-primary-darken-27);
|
|
--bs-alert-border-color: var(--pngx-bg-darker);
|
|
}
|
|
|
|
.table-striped > tbody > tr:nth-of-type(odd) > * {
|
|
color: var(--pngx-body-color-accent);
|
|
}
|
|
|
|
.close, .modal .btn-close, .alert .btn-close {
|
|
text-shadow: 0 1px 0 #666;
|
|
}
|
|
|
|
.modal .btn-close, .alert .btn-close, .toast .btn-close {
|
|
filter: invert(1) grayscale(100%) brightness(200%);
|
|
}
|
|
|
|
.toast, .toast-header {
|
|
background-color: hsla(var(--pngx-primary), calc(var(--pngx-primary-lightness) - 15%), 0.8);
|
|
}
|
|
|
|
.toast,
|
|
.toast .toast-header,
|
|
.toast .btn,
|
|
.toast .btn-close {
|
|
color: var(--pngx-primary-text-contrast);
|
|
}
|
|
|
|
.dropdown-menu {
|
|
--bs-dropdown-color: var(--bs-body-color);
|
|
}
|
|
}
|
|
|
|
body.color-scheme-dark {
|
|
// no custom theme color
|
|
&:not(.primary-light):not(.primary-dark) {
|
|
@include paperless-green-dark-mode;
|
|
|
|
.navbar.bg-primary {
|
|
// navbar is og green in dark mode
|
|
@include paperless-green;
|
|
}
|
|
}
|
|
|
|
@include dark-mode;
|
|
}
|
|
|
|
@media (prefers-color-scheme: dark) {
|
|
body.color-scheme-system {
|
|
// no custom theme color
|
|
&:not(.primary-light):not(.primary-dark) {
|
|
@include paperless-green-dark-mode;
|
|
|
|
.navbar.bg-primary {
|
|
// navbar is og green in dark mode
|
|
@include paperless-green;
|
|
}
|
|
}
|
|
|
|
@include dark-mode;
|
|
}
|
|
}
|