removed like 2000 comments

This commit is contained in:
Guy Sandler 2026-10-18 17:06:19 -07:00
parent 80662e75e8
commit 81e49178aa
8 changed files with 597 additions and 2644 deletions

View File

@ -58,12 +58,8 @@
font-size: 12px;
padding-inline: 6px;
}
/* The native date/time picker icons are themed in dark mode only via
color-scheme (see DARKMODE_CSS in css/darkmodecss.js); light mode keeps the
default dark glyphs on the light surface. */
/* picker icons are themed via color-scheme only in dark mode (see darkmodecss.js) */
.canvasrefined-custom-btn {background: #f5f5f5; border: 1px solid #c7cdd1; border-radius:6px; padding: 2px 8px;}
/* Better sidebar buttons sit on the --bcsidebar surface and use --bcsidebar-text
for labels/icons, so drop the light button chrome and use a subtle hover tint. */
.better-sidebar-btn {background: transparent !important; border-color: transparent !important;}
.better-sidebar-btn:hover {background: color-mix(in srgb, var(--bcsidebar-text) 14%, transparent) !important;}
.canvasrefined-viewmore-btn {display: block;margin:0 auto;margin-top: 8px;}
@ -148,8 +144,6 @@
.canvasrefined-todo-action {border-radius: 5px;}
.canvasrefined-todo-actions {position: absolute; top: 0; right: 0; background: #fff;width:110px;font-weight:bold; color:#000;display:none;z-index:1000;border-radius:3px;border: 1px solid #c7cdd1;padding:10px}
.canvasrefined-todo-actions-btn { border:1px solid transparent; height: 20px;width: 20px;background: none;padding: 0;margin: 0;border-radius:3px;}
/*.canvasrefined-dots-icon {display: block!important;}
.canvasrefined-todo-actions-btn:hover {background: #f5f5f5; border:1px solid #c7cdd1;}*/
.canvasrefined-todo-action, .canvasrefined-todo-action-tag { padding: 4px; margin: -2px 0;display:flex;justify-content: space-between;align-items:center;}
.canvasrefined-todo-action:hover {background: #f5f5f5;cursor:pointer}
.canvasrefined-todo-input {width: 100%!important;box-sizing: border-box!important;border-radius: 5px!important;height: 24px!important;padding:4px!important;margin:0!important;font-size:12px!important}
@ -159,7 +153,6 @@
.canvasrefined-todo-svg {fill:#2d3b45!important}
#canvasrefined-update-msg {margin-top: 5px; display: flex; justify-content: space-between; font-size:15px;background: linear-gradient(115deg, rgb(255, 53, 88, .9), rgb(255, 131, 73, .9), rgb(255, 103, 187, .9)); color: #fff; border-radius:4px; padding: 20px;white-space: pre-line;}
/* Detected-canvas prompt — centered modal with backdrop so it can't be missed */
#canvasrefined-domain-prompt-backdrop {position: fixed!important;inset: 0!important;width: 100%!important;height: 100%!important;background: rgb(0 0 0 / 60%)!important;z-index: 2147483647!important;display: flex!important;align-items: center!important;justify-content: center!important;}
#canvasrefined-domain-prompt {background: #fff!important;border-radius: 14px!important;padding: 24px 28px!important;max-width: 460px!important;width: 90%!important;box-sizing: border-box!important;box-shadow: 0 12px 48px rgb(0 0 0 / 45%)!important;animation: .25s ease canvasrefined-pop;}
@keyframes canvasrefined-pop {0% {transform: scale(.9);opacity: 0} 100% {transform: scale(1);opacity: 1}}
@ -195,7 +188,6 @@
}
}
/* ===== Dashboard notes (Markdown) ===== */
.canvasrefined-notes-toolbar {display:flex;flex-wrap:wrap;gap:2px;padding:6px 8px;align-items:center;background:var(--bcbackground-2,#f5f7f8);border-bottom:1px solid var(--bcborders,#c7cdd1);}
.cr-fmt {border:1px solid transparent;background:transparent;color:var(--bctext-1,#5b6770);font:inherit;font-size:13px;line-height:1;padding:5px 7px;border-radius:4px;cursor:pointer;}
.cr-fmt:hover {background:var(--bcbackground-1,rgba(0,0,0,.06));color:var(--bctext-0,#2d3b45);}
@ -232,7 +224,6 @@
.canvasrefined-dashboard-notes:not(.is-editing) .canvasrefined-notes-toolbar {display:none;}
.canvasrefined-dashboard-notes.is-editing .canvasrefined-notes-rendered {display:none;}
.canvasrefined-dashboard-notes:not(.is-editing) .canvasrefined-notes-editor {display:none;}
/* Quiz safe mode banner (pre-quiz pages) */
.canvasrefined-quiz-safe-banner {
box-sizing: border-box;
margin: 16px 0;
@ -281,15 +272,12 @@
}
.canvasrefined-quiz-safe-dismiss:hover { background: #ececec; }
/* ===== Global Canvas Search ===== */
/* Native global-nav search item — matches Canvas' own nav links. */
.canvasrefined-gs-nav-item { list-style: none; }
.canvasrefined-gs-nav-item .ic-app-header__menu-list-link { cursor: pointer; }
.canvasrefined-gs-nav-item .menu-item-icon-container svg { width: 26px; height: 26px; }
.canvasrefined-gs-nav-item:hover .ic-app-header__menu-list-link { background: #0000004f !important; }
.canvasrefined-gs-nav-item .menu-item__text { font-size: 12px; }
/* Dashboard header trigger — sits just left of the \u22ee options button. */
.canvasrefined-gs-header-btn {
display: inline-flex; align-items: center; gap: 6px;
margin-right: 10px; padding: 6px 12px;
@ -382,36 +370,25 @@
padding: 0 4px; color: var(--bctext-1, #5b6770);
}
/* ===== Grades table: scale down with narrow windows =====
Canvas lays out #grades_summary with content-driven auto sizing plus hard
min-widths (title 150px, details 80px) and nowrap cells (due, score,
details), giving it a ~780px floor below which the whole table overflows
the page instead of shrinking. Switch it to fixed layout with percentage
column widths (set on the header row, which drives fixed layout) and let
tight cells wrap, so the header, body and rows all scale with the
viewport. #assignments scrolls horizontally as a last resort (e.g. while a
what-if score input is open). */
/* Canvas hard-min-widths + nowrap cells give #grades_summary a ~780px floor;
fixed layout with % widths lets it scale with the viewport. */
#grades_summary { table-layout: fixed; width: 100%; }
#grades_summary thead th:nth-child(1) { width: 30%; } /* Name */
#grades_summary thead th:nth-child(2) { width: 12%; } /* Due */
#grades_summary thead th:nth-child(3) { width: 10%; } /* Submitted */
#grades_summary thead th:nth-child(4) { width: 7%; } /* Status */
#grades_summary thead th:nth-child(5) { width: 11%; } /* Score */
#grades_summary thead th:nth-child(6) { width: 3%; } /* asset processors */
#grades_summary thead th:nth-child(7) { width: 15%; } /* Details */
#grades_summary thead th:nth-child(8) { width: 3%; } /* progress */
/* columns: Name, Due, Submitted, Status, Score, asset processors, Details, progress */
#grades_summary thead th:nth-child(1) { width: 30%; }
#grades_summary thead th:nth-child(2) { width: 12%; }
#grades_summary thead th:nth-child(3) { width: 10%; }
#grades_summary thead th:nth-child(4) { width: 7%; }
#grades_summary thead th:nth-child(5) { width: 11%; }
#grades_summary thead th:nth-child(6) { width: 3%; }
#grades_summary thead th:nth-child(7) { width: 15%; }
#grades_summary thead th:nth-child(8) { width: 3%; }
#grades_summary td.due,
#grades_summary td.assignment_score,
#grades_summary td.details { white-space: normal; }
#assignments { overflow-x: auto; }
/* Big strikethrough on checked-off tasks (dashboard list view). Canvas keeps
completed planner items looking identical to unfinished ones — the only cue
is the checkbox itself — so when a task's checkbox is checked, strike its
title through with a thick line and dim the row. :has() matches the
checkbox state reactively, so this also applies live at the moment a task
is checked, before Canvas collapses it into the completed-items section. */
/* Canvas gives no visual cue for a completed planner item; :has() strikes it live. */
.planner-item:has(input[data-testid="planner-item-completed-checkbox"]:checked) {
opacity: 0.7;
}
@ -422,35 +399,22 @@
text-decoration-thickness: 2.5px !important;
}
/* InstUI View (emotion hash css-fkmnqn-view) ships a bottom margin that
leaves a stray gap below the discussion/announcement header card.
Hashed classes can shift between Canvas releases; an unmatched selector
here is simply inert. */
/* hashed InstUI View class leaving a gap below the header card; may shift between releases */
.css-fkmnqn-view {
margin-bottom: 0 !important;
}
/* Shared widget container ("Top"/"Bottom" positions): a full-width flex row
holding one slot per widget; slot widths are the % set in the Widgets tab.
Row margins mirror the notes container's original 18/14 spacing. */
/* one slot per widget; widths are the % set in the Widgets tab */
.canvasrefined-widget-row {display:flex;align-items:stretch;width:100%;box-sizing:border-box;margin:18px 0 14px;column-gap:14px;}
.canvasrefined-widget-slot {min-width:0;box-sizing:border-box;display:flex;flex-direction:column;}
.canvasrefined-widget-slot > * {width:100%;}
/* Equal height across widgets in the shared container: every slot stretches
to the row height and its widget content fills it top-to-bottom. */
.canvasrefined-widget-slot .canvasrefined-dashboard-notes {width:100%;margin:0;height:100%;display:flex;flex-direction:column;}
.canvasrefined-widget-slot .canvasrefined-dashboard-notes .canvasrefined-notes-surface {flex:1;display:flex;flex-direction:column;}
.canvasrefined-widget-slot .canvasrefined-dashboard-notes .canvasrefined-notes-editor,
.canvasrefined-widget-slot .canvasrefined-dashboard-notes .canvasrefined-notes-rendered {flex:1;overflow:auto;}
.canvasrefined-widget-slot .canvasrefined-gpa-card {width:100%;margin:0;box-sizing:border-box;display:block;flex:1 1 auto;min-height:0;}
.canvasrefined-widget-slot .canvasrefined-gpa {margin:0;flex:1 1 auto;min-height:0;overflow:auto;}
/* GPA calculator in container mode ("Top"/"Bottom" positions): the elements
are moved outside the card grid, so the collapsed GPA card becomes a wide
container-style card and the expanded calculator keeps full width. */
.canvasrefined-gpa-card.container-mode {width:100%;box-sizing:border-box;margin:0 0 4px;display:block;}
.canvasrefined-gpa.container-mode {margin:0 0 18px;}
/* Dashboard notes placed inside the card grid (before/after cards): styled
exactly like the GPA card / Canvas course cards — 262px wide, rounded,
card shadow, and the same 36px gutters so it aligns in the grid. */
.canvasrefined-dashboard-notes.in-cards {
width: 262px;
min-height: 260px;
@ -466,12 +430,6 @@
.canvasrefined-dashboard-notes.in-cards .canvasrefined-notes-surface {flex: 1; display: flex; flex-direction: column;}
.canvasrefined-dashboard-notes.in-cards .canvasrefined-notes-editor,
.canvasrefined-dashboard-notes.in-cards .canvasrefined-notes-rendered {flex: 1; resize: none; border: none; outline: none; background: transparent;}
/* Notes placed in the shared widget row get their margins from the row
(see .canvasrefined-widget-slot rules above). */
/* GPA calculator modal (Edit Calculator button): combines the course
calculator with the grade-scale editor, styled like the global search
modal. */
/* ===== GPA calculator modal (rebuilt) ===== */
#canvasrefined-gpa-modal {
--cr-gpa-course-cols: 30px minmax(0,1fr) 80px 58px 118px 16px minmax(88px,auto);
--cr-gpa-accent: var(--ic-brand-primary,#0374b5);
@ -479,7 +437,6 @@
display:flex;align-items:flex-start;justify-content:center;padding:7vh 16px 16px;
}
.cr-gpa-modal {width:min(1080px,96vw);max-height:86vh;display:flex;flex-direction:column;background:var(--bcbackground-0,#fff);color:var(--bctext-0,#2d3b45);border:1px solid var(--bcborders,#c7cdd1);border-radius:16px;box-shadow:0 24px 70px rgba(0,0,0,.4);overflow:hidden;font-size:13px;}
/* Header: title on the left, live GPA tiles on the right */
.cr-gpa-head {display:flex;align-items:center;gap:16px;flex-wrap:wrap;padding:16px 20px;border-bottom:1px solid var(--bcborders,#c7cdd1);}
.cr-gpa-head-titles {display:flex;flex-direction:column;gap:2px;margin-right:auto;min-width:140px;}
.cr-gpa-title {font-size:17px;font-weight:700;}
@ -490,17 +447,14 @@
.cr-gpa-result-label {font-size:10px;font-weight:600;letter-spacing:.07em;text-transform:uppercase;color:var(--bctext-2,#9aa3ab);}
.cr-gpa-close {display:flex;align-items:center;justify-content:center;width:32px;height:32px;flex:none;border:none;background:transparent;color:inherit;border-radius:8px;cursor:pointer;}
.cr-gpa-close:hover {background:rgba(127,127,127,.15);}
/* Body: courses on the left, grade scale on the right; panes scroll alone */
.cr-gpa-body {display:grid;grid-template-columns:minmax(0,2.2fr) minmax(210px,1fr);flex:1;min-height:0;}
.cr-gpa-pane {min-width:0;overflow-y:auto;padding:14px 20px 20px;}
.cr-gpa-pane-scale {border-left:1px solid var(--bcborders,#c7cdd1);padding-left:14px;}
.cr-gpa-pane-head {font-size:11px;font-weight:700;letter-spacing:.08em;text-transform:uppercase;color:var(--bctext-2,#9aa3ab);margin:0 0 10px;}
/* Calculator body moved into the modal: neutralize panel chrome */
.cr-gpa-modal .canvasrefined-gpa {display:block!important;margin:0;padding:0;border:none;box-shadow:none!important;overflow:visible;position:static;background:transparent!important;border-radius:0;}
.cr-gpa-modal .canvasrefined-gpa .canvasrefined-gpa-header {display:none;}
.cr-gpa-modal .canvasrefined-gpa-courses-container {margin:0;width:100%;overflow:visible;}
.cr-gpa-modal .canvasrefined-gpa-courses {display:flex;flex-direction:column;min-width:0;width:100%;}
/* Course rows: shared grid so the column headers line up with the rows */
.cr-gpa-colhead,
.cr-gpa-modal .canvasrefined-gpa-course,
.cr-gpa-modal #canvasrefined-cumulative-gpa {display:grid;grid-template-columns:var(--cr-gpa-course-cols);column-gap:10px;align-items:center;}
@ -508,7 +462,6 @@
.cr-gpa-colhead .cr-gpa-colhead-custom {grid-column:6 / span 2;}
.cr-gpa-modal .canvasrefined-gpa-course {padding:7px 8px;border-radius:10px;}
.cr-gpa-modal .canvasrefined-gpa-course:hover {background:color-mix(in srgb, var(--bctext-0,#2d3b45) 5%, transparent);}
/* Letter badge: color-coded pill driven by data-grade-letter (set in calculateGPA2) */
.cr-gpa-modal .canvasrefined-gpa-letter-grade {width:auto;margin:0;display:flex;align-items:center;justify-content:center;min-height:26px;padding:0 2px;border-radius:8px;font-size:12px;font-weight:700;background:transparent;color:var(--bctext-0,#2d3b45);}
.cr-gpa-modal [data-grade-letter] .canvasrefined-gpa-letter-grade {background:transparent;color:var(--bctext-0,#2d3b45);}
.cr-gpa-modal .canvasrefined-gpa-name {margin:0;width:auto;min-width:0;overflow:hidden;text-overflow:ellipsis;white-space:nowrap;font-size:14px;font-weight:500;}
@ -524,15 +477,12 @@
.cr-gpa-modal .canvasrefined-course-weight:focus {outline:none;border-color:var(--cr-gpa-accent);}
.cr-gpa-modal .canvasrefined-course-customgr {margin:0;width:16px;height:16px;accent-color:var(--cr-gpa-accent);cursor:pointer;}
.cr-gpa-modal .canvasrefined-course-customgr-label {margin:0;font-size:12px;color:var(--bctext-2,#9aa3ab);cursor:pointer;white-space:nowrap;overflow:hidden;text-overflow:ellipsis;}
/* Cumulative row: pulled to the bottom as an emphasized summary row */
.cr-gpa-modal #canvasrefined-cumulative-gpa {order:100;margin-top:10px;padding:12px 8px 4px;border-top:1px dashed var(--bcborders,#c7cdd1);}
.cr-gpa-modal #canvasrefined-cumulative-gpa .canvasrefined-gpa-name {font-weight:700;}
/* Grade scale pane */
.cr-gpa-seg {display:flex;gap:8px;padding:0;background:transparent;margin:0 0 14px;}
.cr-gpa-preset {flex:1;border:1px solid var(--bcborders,#c7cdd1);background:transparent;color:var(--bctext-2,#9aa3ab);border-radius:8px;padding:7px 10px;font-size:13px;font-weight:600;cursor:pointer;font-family:inherit;}
.cr-gpa-preset:hover {color:var(--bctext-0,#2d3b45);}
.cr-gpa-preset.active {background:var(--bcbackground-0,#fff);color:var(--bctext-0,#2d3b45);border-color:var(--bctext-2,#9aa3ab);}
/* Grade scale rows: letter chip + compact "value + unit" fields */
.cr-gpa-scale-head {display:grid;grid-template-columns:40px 1fr 1fr;gap:8px;padding:0 2px 4px;font-size:10.5px;font-weight:600;letter-spacing:.06em;text-transform:uppercase;color:var(--bctext-2,#9aa3ab);}
.cr-gpa-row {display:grid;grid-template-columns:40px 1fr 1fr;gap:8px;align-items:center;padding:2px 0;}
.cr-gpa-row:hover {background:color-mix(in srgb, var(--bctext-0,#2d3b45) 4%, transparent);border-radius:8px;}
@ -549,10 +499,6 @@
.cr-gpa-pane-scale {border-left:none;border-top:1px solid var(--bcborders,#c7cdd1);}
}
/* ===== Generic dashboard widgets: Focus Timer, Breathing, Quotes =====
Shared shell follows the same card look as Notes/GPA: 262px grid cell with
the 36px Canvas gutter when placed before/after the course cards, and a
full-width flowing card when placed in the top/bottom container row. */
.canvasrefined-widget-card {
width: 262px;
min-height: 200px;
@ -583,10 +529,8 @@
.cr-widget-btn {flex:1;border:none;border-radius:8px;padding:9px 12px;font:inherit;font-weight:600;font-size:13px;cursor:pointer;background:var(--ic-brand-primary,#0374b5);color:#fff;}
.cr-widget-btn:hover {filter:brightness(1.07);}
.cr-widget-btn-ghost {background:transparent;color:var(--bctext-0,#2d3b45);border:1px solid var(--bcborders,#c7cdd1);}
/* Timer engine (Focus Timer + Breathing Breaks) */
.cr-time-box {position:relative;margin:14px 14px 0;border-radius:12px;background:color-mix(in srgb, var(--bctext-0,#2d3b45) 6%, transparent);border:1px solid var(--bcborders,#c7cdd1);overflow:hidden;}
/* The whole time rectangle is the progress bar, tinted with the dark-mode
link color so it matches the active theme in both light and dark mode. */
/* the time rectangle is the progress bar, tinted with the theme link color */
.cr-time-box .cr-timer-progress-bar {position:absolute;left:0;top:0;bottom:0;width:0;background:color-mix(in srgb, var(--bclinks,#0374b5) 32%, transparent);border-right:2px solid color-mix(in srgb, var(--bclinks,#0374b5) 80%, transparent);}
.cr-timer-time {position:relative;z-index:1;font-size:44px;font-weight:700;text-align:center;letter-spacing:.02em;font-variant-numeric:tabular-nums;padding:22px 14px;line-height:1;color:var(--bctext-0,#2d3b45);}
.cr-breath-display {padding:12px 14px 6px;}
@ -596,7 +540,7 @@
.cr-timer-preset.active {background:color-mix(in srgb, var(--bclinks,#0374b5) 18%, transparent);border-color:var(--bclinks,#0374b5);color:var(--bclinks,#0374b5);}
.cr-timer-custom-row {display:flex;gap:8px;padding:10px 14px 0;align-items:center;}
.cr-timer-custom-row[hidden] {display:none;}
/* Compact clock entry: 0 : 00 : 00, click a segment to edit it. */
/* compact 0 : 00 : 00 entry: click a segment to edit it */
.cr-time-input {display:flex;align-items:center;justify-content:center;gap:1px;flex:1;min-width:0;border:1px solid var(--bcborders,#c7cdd1);border-radius:8px;padding:4px 8px;background:color-mix(in srgb, var(--bctext-0,#2d3b45) 5%, transparent);}
.cr-time-input:focus-within {border-color:var(--bclinks,#0374b5);box-shadow:0 0 0 2px color-mix(in srgb, var(--bclinks,#0374b5) 22%, transparent);}
.cr-tf {width:2.4ch;min-width:0;border:none;background:transparent;color:var(--bctext-0,#2d3b45);font:inherit;font-size:15px;font-weight:700;line-height:1.2;text-align:center;padding:0;border-radius:4px;}
@ -605,7 +549,7 @@
.cr-tf-colon {font-size:15px;font-weight:700;color:var(--bctext-2,#9aa3ab);padding-bottom:1px;}
.cr-timer-custom-row .cr-widget-btn {flex:none;padding:7px 13px;}
.cr-timer-controls {display:flex;gap:8px;padding:12px 14px 14px;}
/* Breathing Breaks: 4s in / 6s out, colour shifts green -> blue when exhaling */
/* 4s in / 6s out; colour shifts green -> blue while exhaling */
.canvasrefined-breathing {background:linear-gradient(160deg, color-mix(in srgb, #6ea8ff 14%, var(--bcbackground-1,#fff)), var(--bcbackground-1,#fff));}
.cr-breath-stage {display:flex;align-items:center;justify-content:center;padding:20px 14px 6px;}
.cr-breath-circle {position:relative;width:112px;height:112px;border-radius:50%;display:flex;align-items:center;justify-content:center;background:radial-gradient(circle at 50% 40%, #74e3c4, #2fb595);box-shadow:0 0 18px 2px rgba(65,209,175,.4);}
@ -635,8 +579,6 @@
.canvasrefined-breathing.is-running .cr-breath-phase-out {animation: cr-breath-out-label 10s ease-in-out infinite;}
@keyframes cr-breath-in-label {0%{opacity:1;}38%{opacity:1;}44%{opacity:0;}100%{opacity:0;}}
@keyframes cr-breath-out-label {0%{opacity:0;}38%{opacity:0;}44%{opacity:1;}94%{opacity:1;}100%{opacity:0;}}
/* Breathing layout: circle + time stacked above the controls (card mode), and
circle + time on the left with the controls on the right in Top/Bottom rows. */
.cr-breath-layout {display:flex;flex-direction:column;flex:1;min-height:0;}
.cr-breath-left {display:flex;flex-direction:column;align-items:center;justify-content:center;}
.cr-breath-right {display:flex;flex-direction:column;justify-content:center;}
@ -646,8 +588,6 @@
.canvasrefined-breathing.container-mode .cr-breath-stage {padding:8px 0;}
.canvasrefined-breathing.container-mode .cr-timer-presets {padding-top:0;}
.canvasrefined-breathing.container-mode .cr-timer-controls {padding-bottom:0;}
/* Daily Quote: text scales with the widget's own width (small grid cell vs.
full-width container row), using container-query units. */
.canvasrefined-quotes {container-type:inline-size;background:linear-gradient(150deg, color-mix(in srgb, #b98cff 14%, var(--bcbackground-1,#fff)), var(--bcbackground-1,#fff));}
.cr-quote-body {padding:clamp(12px,4.5cqw,26px);display:flex;flex-direction:column;gap:clamp(4px,1.6cqw,12px);flex:1;justify-content:center;}
.cr-quote-mark {font-size:clamp(20px,11cqw,44px);line-height:.5;font-weight:800;color:color-mix(in srgb, var(--bclinks,#0374b5) 55%, transparent);}

View File

@ -757,7 +757,6 @@ h6,
.canvasrefined-todo-actions,
.css-md78hg-colHeader,
.css-ywdg6k-view-rowHeader,
/* Assignment page rubric styling */
[data-testid="rubric-assessment-traditional-view"] > div:first-of-type [class$="-text"],
[id^="rubric-header-"] [class$="-text"],
[data-testid="rubric-assessment-traditional-view"] tbody tr td:first-child > div > div:first-child [class$="-text"] {
@ -990,7 +989,6 @@ ul#question_list li.current_question,
[data-testid="rubric-tab"] [class$="-baseButton__content"],
[data-testid="rubric-tab"] [class$="-text"],
button[data-cid~="CloseButton"] > [class$="-baseButton__content"],
/* sidebar course listing */
.css-8bodfv-text {
color:var(--bctext-2)!important
}
@ -1217,43 +1215,27 @@ hr {
.event-details strong {
color: var(--bctext-0) !important;
}
/* Theme the native date/time picker icons so they stay visible on the dark
sidebar surface. Applied in dark mode only — light mode keeps the default
dark glyphs (see css/content.css).
color-scheme: dark is the cross-browser way to flip the native picker icon
to a light glyph. Firefox 109+ ignores ::-webkit-calendar-picker-indicator
(the icon lives in a closed Shadow DOM), so a filter alone does nothing
there; color-scheme fixes both Firefox and modern Chrome. Do NOT also apply
an invert filter — color-scheme already makes the glyph light, and inverting
would flip it back to dark in Chrome. */
/* color-scheme flips the native picker glyph; Firefox ignores the webkit
pseudo-element, so don't also invert it. */
#better-todo-new-task-date,
#better-todo-new-task-time {
color-scheme: dark !important;
color: var(--bctext-0) !important;
}
/* Dashboard list view header (Today / Add To Do / Show My Grades /
opportunities): Canvas paints the icon glyphs a dark ink color that
disappears on the dark glass header bar. Recolor the header text and
its icon SVGs to the theme text color. */
/* header glyphs are painted dark ink; recolor text + icon SVGs */
.PlannerHeader-styles__root {
color: var(--bctext-0) !important;
}
.PlannerHeader-styles__root svg {
fill: var(--bctext-0) !important;
}
/* The "Today" button's label span carries Canvas's dark ink color from its
emotion class, which beats the inherited root color above — dark text on
the dark header bar. Force the whole button chain to the theme text color. */
/* the label span's emotion class out-specifies the inherited color */
.PlannerHeader-styles__root button,
.PlannerHeader-styles__root button span {
color: var(--bctext-0) !important;
}
/* Solid themed surfaces for the header buttons. Canvas leaves the icon
buttons (Add To Do / Show My Grades / opportunities) fully transparent
and paints the Today button an unthemed color — on the dark header bar
they need solid backgrounds to read as buttons. #planner-today-btn:hover
is listed separately because the ID selector on the base background rule
above would otherwise out-specify the class-only :hover rule. */
/* icon buttons are transparent and Today is unthemed; both need a surface.
The :hover rule is split out because the ID rule would out-specify it. */
.PlannerHeader-styles__root button {
background: var(--bcbackground-1) !important;
border: 1px solid var(--bcborders) !important;
@ -1263,57 +1245,36 @@ hr {
#planner-today-btn:hover {
background: var(--bcbackground-2) !important;
}
/* The "Today" button keeps its filled surface (from the rule above) but
gets no outline. Two borders were boxing it in: the themed border the
rule above paints on the button itself, and — the sneaky one —
Instructure's Button variant draws its own light-gray border
(rgb(232,234,236)) on the inner [class$="-baseButton__content"] span,
which reads as a bright 1px ring on the dark chip. The icon buttons'
content spans carry no border, so only Today needs this. Transparent
(instead of border: none) keeps the button's exact dimensions. */
/* InstUI draws its own light border on the inner baseButton__content span;
transparent instead of none keeps the button's size. */
#planner-today-btn,
#planner-today-btn [class$="-baseButton__content"] {
border-color: transparent !important;
}
/* Instructure's Button variant paints its inner content span white (and a
light gray on hover / white + inset shadow on active). That span covers
the themed button background painted above, so the "Today" button still
rendered as a white box. Flatten the content span in every state so the
button's own surface shows through. */
/* the content span paints white in every state, hiding the themed surface */
.PlannerHeader-styles__root button [class$="-baseButton__content"],
.PlannerHeader-styles__root button:hover [class$="-baseButton__content"],
.PlannerHeader-styles__root button:active [class$="-baseButton__content"] {
background: transparent !important;
box-shadow: none !important;
}
/* InstUI Button whose inner content span ships a light background and its
own border, which reads as a bright chip on the dark theme. Paint it with
the themed button surface, drop the border entirely, and force the theme
text color: Canvas sets its own dark ink color on the content span, which
left labels/icons dark-on-dark inside the dark chip. */
/* content span ships a light background + border and sets dark ink */
.css-1ta5ds2-baseButton__content {
background: var(--bcbackground-1) !important;
border: none !important;
color: var(--bctext-0) !important;
}
/* Dashboard list-view trays ("Add To Do" / "My Grades" opened from the
header buttons): Instructure UI renders Tray panels as body-level
portals — body > span > span[...-tray] — with a hardcoded white
background. Paint the tray panel with the theme background; the tray
contents already pick up the theme text color. */
/* trays are body-level portals (body > span > span[...-tray]) with a hardcoded
white background */
body > span > span[class*="-tray"] {
background: var(--bcbackground-0) !important;
}
/* The Add To Do form ships its own <style> tag hardcoding background
#FFFFFF on its root. */
/* the form ships its own <style> hardcoding #FFFFFF on its root */
.UpdateItemTray-styles__root {
background: var(--bcbackground-0) !important;
}
/* Immersive Reader button (in the nav-toggle + breadcrumbs bar): an InstUI
Button whose emotion class hashes change between Canvas releases, so
target the stable mount point and attribute-suffix class names instead.
The button and its inner content span carry a light surface, dark ink
text and a black icon glyph, which are unreadable on the dark theme. */
/* target the stable mount point + attribute-suffix classes: emotion hashes
change between Canvas releases */
#immersive_reader_mount_point button[class$="-baseButton"],
#immersive_reader_mount_point button[class$="-baseButton"] > span:first-child {
background: var(--bcbackground-1) !important;
@ -1321,44 +1282,32 @@ body > span > span[class*="-tray"] {
border: 1px solid var(--bcborders) !important;
box-shadow: none !important;
}
/* The icon glyph is hardcoded black (fill="#000000" attribute); recolor it
to the theme text color. The blue accent paths stay as-is — they read
fine on dark. */
/* glyph is hardcoded fill="#000000"; the blue accent paths stay as-is */
#immersive_reader_mount_point button[class$="-baseButton"] svg path[fill="#000000"] {
fill: var(--bctext-0) !important;
}
/* InstUI TextInput / Select facades (Title, Date, Time, Course fields):
white surface, dark ink, gray border. Repaint with the theme surface,
text, and border colors — the calendar / arrow icons inside use
currentColor, so they follow. Attribute-contains matching because
emotion appends animation-state classes (e.g. transition--*) after the
component class. */
/* TextInput/Select facades: repaint surface/text/border; inner icons use
currentColor. Attribute-contains because emotion appends state classes. */
[class*="-textInput__facade"] {
background: var(--bcbackground-1) !important;
border-color: var(--bcborders) !important;
color: var(--bctext-0) !important;
}
/* Field labels (Title / Date / Time / Course / Details) and the date-time
summary message keep Canvas's dark ink. */
/* field labels and the date-time summary keep Canvas's dark ink */
[class$="-formFieldLayout__label"],
[class$="-formFieldMessage"] {
color: var(--bctext-1) !important;
}
/* InstUI ContextView popovers — the opportunities popup behind "Show My
Grades" and the date-picker calendar behind the Date field: white card
with dark text. Theme the card; descendants without their own ink
color (weekday headers, month label) inherit from here. */
/* ContextView popovers (opportunities, date picker): theme the card,
descendants without their own ink inherit from it */
[class*="-contextView__content"] {
background: var(--bcbackground-0) !important;
color: var(--bctext-0) !important;
}
/* The opportunities popup's tab labels carry their own dark ink. */
[class*="-contextView__content"] [class$="-view-tab"] {
color: var(--bctext-0) !important;
}
/* Flatten the white InstUI View surfaces nested inside those popovers
(the calendar body, the opportunities tab strip, the panel content) so
the themed card shows through. */
/* flatten the white View wrappers so the themed card shows through */
[class*="-contextView__content"] [class*="-view--inlineBlock"],
[class*="-contextView__content"] [class*="-view--block"],
[class*="-contextView__content"] [class*="-view-tabs__container"],
@ -1366,9 +1315,7 @@ body > span > span[class*="-tray"] {
[class*="-contextView__content"] [class*="-calendar__navigation"] {
background: transparent !important;
}
/* Calendar day chips: white squares with dark numbers. Flatten them and
recolor; the selected day keeps a filled chip (matched structurally via
aria-selected, since the chip's emotion class is a content hash). */
/* day chips are white squares; the selected one is matched via aria-selected */
[class*="-calendarDay__day"] {
background: transparent !important;
color: var(--bctext-0) !important;
@ -1377,11 +1324,8 @@ button[aria-selected="true"] > [class*="-calendarDay__day"] {
background: var(--bclinks) !important;
color: #ffffff !important;
}
/* InstUI Select dropdowns (Time / Course) open body-level popover portals
with white View wrappers and white option rows around the options list.
Theme the list, flatten the wrappers and rows; the wrappers' emotion
classes carry no semantic suffix, so they are matched structurally with
:has() on the options list they contain (portal pattern: body > span). */
/* Select dropdowns open body-level portals; wrappers are matched structurally
with :has() on the options list (their emotion classes carry no suffix) */
[class*="-options__list"] {
background: var(--bcbackground-0) !important;
color: var(--bctext-0) !important;
@ -1400,17 +1344,12 @@ button[aria-selected="true"] > [class*="-calendarDay__day"] {
body > span span:has([class*="-options__list"]) {
background: transparent !important;
}
/* Planner "Submitted" pill in the completed-items row: InstUI renders it
as a white chip with gray text. */
/* "Submitted" pill renders as a white chip with gray text */
.BadgeList-styles__item [class*="-pill"] {
background: var(--bcbackground-2) !important;
color: var(--bctext-1) !important;
}
/* Flash alert toasts (.flashalert-message, e.g. "Nothing planned today.
Selecting next item."): Canvas renders them as white cards with dark
text, unthemed in dark mode. Paint them with the theme background and
text color; the inner div[open] is the alert card itself. The close X
glyph inherits currentColor from the button. */
/* flash toasts render as white cards; the inner div[open] is the card */
.flashalert-message > div {
background: var(--bcbackground-0) !important;
color: var(--bctext-0) !important;
@ -1425,29 +1364,10 @@ body > span span:has([class*="-options__list"]) {
.flashalert-message > div button svg {
fill: var(--bctext-0) !important;
}
/* Global Announcements page (…/account_notifications): the Current/Recent
tabs come from Instructure UI. Canvas paints the tab labels ("Current" /
"Recent") and the panel caption ("Announcements from the past four
months") with its dark ink, and the active tab panel's content wrapper
(the direct div child of #currentTab/#pastTab) gets a white surface —
all unreadable in dark mode. The panel ids and aria-controls values are
stable; the emotion class hashes are not, so they are not used.
The white surface actually comes from the outer tabs container
(.css-gpxu0l-view-tabs__container, style background:#fff) that wraps
both the tab strip (.css-1baf0tq-view-tabs) and the panels — it is
themed via the stable "view-tabs__container" class fragment, scoped
to this page's panels with :has() so other Instructure UI tabs
elsewhere in Canvas are untouched.
.notification_account_content is the account notification card used on
this page and in the dashboard announcement banner: Canvas sets dark
ink on the card chain (.ic-notification down through
.notification_message and .notification_account_content_text), leaving
the announcement body and the "This is an announcement from…" line
invisible on the themed dark card background. Recolor the body text to
the theme text color, keep the h2 title at the brighter heading color
(an ancestor rule below would otherwise dim it), and mute the meta
line. These class rules also fix the same markup in the dashboard
banner. */
/* Global Announcements page: tab labels, panel caption and the white tabs
container are unthemed. The stable "view-tabs__container" class fragment is
scoped with :has() so other InstUI tabs are untouched. The account
notification card rules here also fix the dashboard announcement banner. */
div[class*='view-tabs__container']:has(#currentTab, #pastTab),
#currentTab>div,
#pastTab>div {
@ -1487,52 +1407,38 @@ div[class*='view-tabs__container']:has(#currentTab, #pastTab),
.notification_account_content a {
color: var(--bclinks) !important;
}
/* Grades page: opening the comment tray marks the row with
.selected-assignment, which Canvas paints light blue (#e0ebf5) with a
.3s background transition — reads as a white row in dark mode. Repaint
it as the theme's raised surface so the highlight stays visible but
dark. */
/* opening the comment tray paints .selected-assignment light blue */
#grades_summary tr.selected-assignment {
background-color: var(--bcbackground-2) !important;
}
/* Grades page (…/courses/:id/grades): the comment chip in each assignment
row (speech-bubble icon + count, .toggle_comments_link) keeps Canvas's
light-gray pill background and border in dark mode; repaint it as a
theme chip. */
/* comment chip keeps Canvas's light-gray pill background + border */
.toggle_comments_link,
.toggle_comments_link:hover {
background: var(--bcbackground-2) !important;
border-color: var(--bcborders) !important;
}
/* Grades page rubric table borders are white by default. */
.rating-tier,
.react-rubric td,
.react-rubric th,
.rating-all-footer,
/* Assignment page rubric table borders */
[data-testid="rubric-assessment-traditional-view"],
[data-testid="rubric-assessment-traditional-view"] thead td,
[data-testid="rubric-assessment-traditional-view"] tbody tr,
[data-testid="rubric-assessment-traditional-view"] tbody td,
[data-testid="traditional-view-criterion-ratings"] > div > div,
/* Modals */
[class$="-modal"],
[class$="-modalHeader"]
{
border-color: var(--bcborders) !important;
}
/* Grades page "late"/"missing" status pills: InstUI renders the inner pill
as a white chip with colored text. The emotion class hashes change between
Canvas releases, so match the stable "-pill" fragment scoped under the
server-rendered status cell. */
/* inner pill is a white chip; match the stable "-pill" fragment under the
server-rendered status cell (emotion hashes change per release) */
td.status [class*="-pill"],
td.status [class*="-pill"]:hover,
/* Assignment page rubric table body */
[data-testid="rubric-assessment-traditional-view"] tbody {
background: var(--bcbackground-2) !important;
color: var(--bctext-1) !important;
}
/* Assignment page rubric headers and modal styling */
[data-testid="rubric-assessment-traditional-view"] > div:first-of-type,
[id^="rubric-header-"],
[class$="-modal"],
@ -1540,7 +1446,6 @@ td.status [class*="-pill"]:hover,
background: var(--bcbackground-1) !important;
color: var(--bctext-0) !important;
}
/* Modal overlay */
[class*="-mask"] {
background: rgba(0, 0, 0, 0.60) !important;
}

View File

@ -6,7 +6,7 @@ h1, h2, p, body{margin:0;padding:0}
h1 {font-size:30px;}
h2 {font-size:24px;}
.option input{display:none;}
/* Knob state for every big toggle (main options AND tab pages like Report issue) */
/* knob state for every big toggle (main options and tab pages) */
.option input:nth-of-type(1).checked ~ .slider .sliderknob{background-color:#e1e1e12e;}
.option input:nth-of-type(2).checked ~ .slider .sliderknob{transform:translate(18px);background-color:#8dd28d;}
.option{display:flex;align-items:center;}
@ -36,7 +36,6 @@ a.option-container:hover {background: #333}
.options-left, .options-right {width: 50%;}
.customDomain {font-weight:600}
/* Canvas URL list — one text box per school */
#custom-domain-list {display: flex;flex-direction: column;gap: 6px;margin-top: 8px}
.domain-row {display: flex;gap: 6px;align-items: center}
.domain-row input {flex: 1;min-width: 0;box-sizing: border-box;font-size: 12px;background: var(--inputbg);border: none;padding: 8px;color: #e2e2e2;border-radius: 7px;font-family: inherit}
@ -86,19 +85,12 @@ h2 {margin-top: 20px;font-weight:600}
#todo_timeframe option {background:#1e1e1e;color:#e2e2e2;}
#todo_timeframe option:checked,
#todo_timeframe option:hover {background:#2e2e2e;color:#fff;}
/* Custom timeframe inputs, shown under the Time frame dropdown when "Custom" is selected */
.custom-tf-wrap {display:none;flex-direction:column;gap:6px;}
.custom-tf-wrap.visible {display:flex;}
.custom-tf-row {display:flex;align-items:center;gap:6px;}
.custom-tf-row input {flex:none;width:58px;font-size:12px;background:var(--inputbg);border:none;padding:6px;color:#e2e2e2;border-radius:6px;font-family:inherit;text-align:right;box-sizing:border-box;color-scheme:dark;}
.custom-tf-row input::-webkit-outer-spin-button, .custom-tf-row input::-webkit-inner-spin-button {opacity:1;}
/* Collapsible "More options" section for the Better Todo List sub-options */
.todo-more-options {margin-top: 7px;}
/* Celebrations box — effect picker + amount for task completion animations */
/* The big "Celebration" toggle is the whole box header; type/amount rows hide when it's off. */
/* The two controls below mirror #todo_timeframe exactly (same font, padding,
radius, colors and full-width stacked layout) so they read like the popup's
other dropdowns. */
.celebration-multiselect {position:relative;}
.celebration-multiselect-btn {display:flex;align-items:center;justify-content:space-between;gap:8px;font-size:12px;background:var(--inputbg);color:#e2e2e2;border:none;border-radius:7px;padding:6px 8px;font-family:inherit;width:100%;box-sizing:border-box;margin-top:2px;margin-bottom:6px;cursor:pointer;text-align:left;}
.celebration-multiselect-btn svg {flex:none;transition:transform .15s ease;}
@ -106,7 +98,6 @@ h2 {margin-top: 20px;font-weight:600}
.celebration-multiselect-menu {display:none;position:absolute;top:calc(100% + 4px);left:0;right:0;z-index:60;background:#1e1e1e;border-radius:7px;padding:5px 0;max-height:180px;overflow-y:auto;box-shadow:0 6px 18px rgba(0,0,0,.45);}
.celebration-multiselect.open .celebration-multiselect-menu {display:block;}
.celebration-multiselect.flip-up .celebration-multiselect-menu {top:auto;bottom:calc(100% + 4px);}
/* Menu rows mirror the native option colors (#1e1e1e idle, #2e2e2e hover) used by the other dropdowns */
.celebration-option {display:flex;align-items:center;gap:7px;padding:5px 10px;font-size:12px;color:#e2e2e2;cursor:pointer;white-space:nowrap;user-select:none;}
.celebration-option:hover {background:#2e2e2e;color:#fff;}
.celebration-option input {accent-color:#56caf0;cursor:pointer;margin:0;}
@ -329,7 +320,6 @@ input[type="checkbox"]:checked {background: #8dd28d;}
}
}
/* ===== Header feature search ===== */
.header-search { position: relative; margin-left: auto; display: flex; align-items: center; gap: 8px; width: 170px; max-width: 42%; background: var(--inputbg); border-radius: 8px; padding: 7px 10px; box-sizing: border-box; }
.header-search-icon { color: #9a9a9a; flex: none; }
.header-search:focus-within { box-shadow: 0 0 0 1.5px #56Caf0; }
@ -345,7 +335,6 @@ input[type="checkbox"]:checked {background: #8dd28d;}
.search-result.empty:hover { background: none; }
.search-highlight { outline: 2px solid #56Caf0; outline-offset: 2px; border-radius: 8px; animation: search-pulse 1.8s ease-out; }
@keyframes search-pulse { 0% { box-shadow: 0 0 0 0 #56Caf099; } 40% { box-shadow: 0 0 0 6px #56Caf000; } 100% { box-shadow: 0 0 0 0 #56Caf000; } }
/* ===== Quiz Safe Mode info bubble ===== */
.cr-info-bubble {
display: inline-flex;
align-items: center;
@ -386,40 +375,28 @@ input[type="checkbox"]:checked {background: #8dd28d;}
.cr-info-bubble:hover .cr-info-bubble-text,
.cr-info-bubble:focus .cr-info-bubble-text { visibility: visible; opacity: 1; }
/* Widget container-order strips (Widgets tab): boxes sized by each widget's
% of the shared container, separated by draggable dividers. */
.widget-order-strip {display:flex;align-items:stretch;width:100%;height:44px;margin-top:6px;}
.wos-item {border:1px solid #ffffff2e;background:var(--inputbg);border-radius:7px;display:flex;align-items:center;padding:0 10px;font-size:12px;color:#e2e2e2;min-width:0;overflow:hidden;white-space:nowrap;cursor:grab;user-select:none;}
.wos-item.dragging {opacity:.45;}
.wos-divider {flex:0 0 6px;width:6px;align-self:stretch;margin:0 5px;border-radius:3px;background:#8a8a8a;cursor:col-resize;}
.wos-divider:hover {background:#e2e2e2;}
/* Widget order box (Widgets tab): one shared "Widget order" rectangle with
a section per area (Top / Before cards / After cards / Bottom); each
section shows only when 2+ enabled widgets share that area. */
.widget-order-section + .widget-order-section {margin-top: 16px;}
.widget-order-label {font-size: 12px;color: #c7c7c7;}
.widget-order-strip {margin-top: 6px;}
/* Before/after strips: sequence only, so boxes share the width evenly with
a gap between them instead of draggable dividers. */
.widget-order-strip[data-area="cards_start"],
.widget-order-strip[data-area="cards_end"] {column-gap: 8px;}
.widget-order-strip[data-area="cards_start"] .wos-item,
.widget-order-strip[data-area="cards_end"] .wos-item {flex: 1 1 0;}
/* Widget sections (Widgets tab): two side-by-side columns; add future
widgets as one more .option-container inside .widgets-grid. */
.widgets-grid {display:grid;grid-template-columns:minmax(0,1fr) minmax(0,1fr);gap:8px;align-items:stretch;margin-top:8px;}
.widgets-grid .option-container {margin-top:0;box-sizing:border-box;min-width:0;}
/* Widget position dropdowns (Widgets tab) — mirror #todo_timeframe exactly:
same font, padding, radius, colors and full-width stacked layout. */
.widget-pos {font-size:12px;background:var(--inputbg);color:#e2e2e2;border:none;border-radius:7px;padding:6px 8px;font-family:inherit;width:100%;box-sizing:border-box;margin-top:2px;margin-bottom:6px;color-scheme:dark;}
.widget-pos option {background:#1e1e1e;color:#e2e2e2;}
.widget-pos option:checked,
.widget-pos option:hover {background:#2e2e2e;color:#fff;}
/* Inline rows: the label sits on the same line as its control. */
.widget-inline-row {display:flex;align-items:center;gap:8px;}
.widget-inline-label {flex:none;}
.widget-inline-select {flex:1;min-width:0;margin-top:0;margin-bottom:0;}
/* Compact clock entry (preset lengths), matching the on-canvas widget. */
/* compact clock entry, matching the on-canvas widget */
.popup-time-input {display:flex;align-items:center;justify-content:center;gap:1px;flex:1;min-width:0;background:var(--inputbg);border-radius:7px;padding:4px 6px;}
.popup-time-input:focus-within {box-shadow:0 0 0 2px rgba(86,202,240,.35);}
.popup-tf {width:2.2ch;min-width:0;border:none;background:transparent;color:#e2e2e2;font:inherit;font-size:13px;font-weight:700;text-align:center;padding:0;border-radius:4px;}

View File

@ -72,7 +72,6 @@ chrome.runtime.onInstalled.addListener(function () {
"custom_assignments_overflow": ["custom_assignments"],
"grade_hover": false,
"card_letter": true,
// "hide_completed": false,
"hide_completed_cards": false,
"num_todo_items": 10,
"custom_font": { "link": "", "family": "" },
@ -94,7 +93,6 @@ chrome.runtime.onInstalled.addListener(function () {
"D-": { "cutoff": 60, "gpa": .7 },
"F": { "cutoff": 0, "gpa": 0 }
},
// "todo_overdues": false,
"card_overdues": false,
"relative_dues": false,
"equal_height_cards": false,
@ -118,7 +116,6 @@ chrome.runtime.onInstalled.addListener(function () {
"custom_font_skip_p": false,
"device_dark": false,
"cumulative_gpa": { "name": "Cumulative GPA", "hidden": false, "weight": "dnc", "credits": 999, "gr": 3.21 },
// "show_updates": false,
"card_method_date": false,
"card_method_dashboard": true,
"card_limit": 25,
@ -170,7 +167,6 @@ chrome.runtime.onInstalled.addListener(function () {
newLocalOptions[option] = default_options["local"][option];
})
// migrate old setting name
if (sync["nasaFitToScreen"] !== undefined && sync["fitImageToScreen"] === undefined) {
newSyncOptions["fitImageToScreen"] = sync["nasaFitToScreen"];
}
@ -192,8 +188,7 @@ chrome.runtime.onInstalled.addListener(function () {
});
});
// The NASA APOD API with the demo key is limited to 30 requests/hour and 50/day.
// Calls are serialized through this worker; the API's own 429 responses handle limiting.
// APOD demo key allows 30 req/hour, 50/day; the API's own 429s do the limiting.
chrome.runtime.onMessage.addListener((message, sender, sendResponse) => {
if (message?.type === "getNasaBackground") {
getNasaBackground().then(sendResponse);
@ -222,7 +217,7 @@ async function getNasaBackground() {
const cached = await chrome.storage.local.get([cacheKey, metadataKey]);
if (cached[cacheKey]) return cached[cacheKey];
// Don't re-probe dates the API already told us don't exist
// never re-probe dates the API reported as missing
const missingKey = `nasa_apod_missing_${dateStr}`;
const missing = await chrome.storage.local.get(missingKey);
if (missing[missingKey]) {
@ -242,8 +237,7 @@ async function getNasaBackground() {
if (!url) return null;
const result = { url, scale: 100, date: dateStr };
const meta = { title: data.title || "", date: data.date || dateStr, copyright: data.copyright || "", explanation: data.explanation || "" };
// Write image + metadata atomically so the info overlay never sees a
// cached image with missing metadata.
// one write, so the overlay never sees an image without its metadata
await chrome.storage.local.set({ [cacheKey]: result, [metadataKey]: meta });
return result;
}
@ -272,10 +266,7 @@ async function callNasaApi(dateStr) {
return await response.json().catch(() => null);
}
// --- Daily quote (stoic.tekloon.net) ---------------------------------------
// Cached in storage.local and refreshed at most once per local calendar day.
// Fetched from the extension worker (host_permissions) because the endpoint
// does not send CORS headers, so a page-context fetch would be blocked.
// Cached in storage.local for one day; fetched from the worker (no CORS headers).
function dailyQuoteTodayKey() {
const d = new Date();
return d.getFullYear() + "-" + String(d.getMonth() + 1).padStart(2, "0") + "-" + String(d.getDate()).padStart(2, "0");
@ -290,7 +281,6 @@ async function getDailyQuote() {
cached = st && st.daily_quote;
} catch (e) { /* ignore storage issues */ }
// Once-a-day: reuse today's cached quote without hitting the network.
if (cached && cached.date === today && cached.quote) return cached;
if (dailyQuoteInFlight) return dailyQuoteInFlight;
@ -308,7 +298,6 @@ async function getDailyQuote() {
return entry;
} catch (e) {
console.warn("[CanvasRefined] Daily quote fetch failed:", e);
// Fall back to the previous day's quote rather than losing it.
return cached || null;
} finally {
dailyQuoteInFlight = null;

File diff suppressed because it is too large Load Diff

View File

@ -1,15 +1,5 @@
/*
CanvasRefined - lightweight Markdown renderer for dashboard notes.
Renders a small, notes-friendly subset of Markdown to HTML:
headings, bold, italic, strikethrough, inline code, fenced code blocks,
links, images, autolinks, blockquotes, ordered/unordered lists, task
lists, horizontal rules, and paragraphs.
All user-supplied text is HTML-escaped before any formatting is applied,
and links/images are URL-sanitized, so the returned HTML is safe to assign
via innerHTML. Exposes window.renderMarkdown(text) -> html.
*/
/* Lightweight Markdown -> HTML for dashboard notes: text is escaped first and
URLs sanitized, so the result is safe for innerHTML. */
(function () {
"use strict";
@ -28,7 +18,6 @@ via innerHTML. Exposes window.renderMarkdown(text) -> html.
if (/^(https?:|mailto:|ftp:|tel:)/i.test(u)) return u;
if (/^(javascript:|vbscript:|file:|data:)/i.test(u)) return "#";
if (/^[#/?]/.test(u)) return u;
// Block any other explicit protocol we did not whitelist.
if (/^[a-z][a-z0-9+.\-]*:/i.test(u)) return "#";
return u;
}
@ -37,55 +26,43 @@ via innerHTML. Exposes window.renderMarkdown(text) -> html.
if (src == null) return "";
src = String(src).replace(/\r\n/g, "\n").replace(/\r/g, "\n");
// Stash protected HTML (code blocks/spans, autolinks) behind NUL-delimited
// tokens so they survive escaping and inline formatting untouched.
// Stash protected HTML behind NUL tokens so escaping can't touch it.
const stash = [];
const keep = (html) => {
stash.push(html);
return "\u0000" + (stash.length - 1) + "\u0000";
};
// 1. Fenced code blocks: ```lang\n code ```
src = src.replace(/```([\w-]*)\n?([\s\S]*?)```/g, (m, lang, code) => {
code = code.replace(/^\n/, "").replace(/\n$/, "");
const langAttr = lang ? ` class="language-${escapeHtml(lang)}"` : "";
return keep(`<pre><code${langAttr}>${escapeHtml(code)}</code></pre>`);
});
// 2. Inline code: `code`
src = src.replace(/`([^`\n]+)`/g, (m, code) => keep(`<code>${escapeHtml(code)}</code>`));
// 3. Autolinks: <https://example.com>
src = src.replace(/<(https?:\/\/[^\s<>]+)>/g, (m, url) => {
const safe = escapeHtml(sanitizeUrl(url));
return keep(`<a href="${safe}" target="_blank" rel="noopener noreferrer">${escapeHtml(url)}</a>`);
});
// 4. Inline formatting, applied to escaped text so nothing the user
// typed can become live HTML. The URL capture allows one level of
// balanced parentheses, e.g. https://en.wikipedia.org/wiki/Foo_(bar).
// Runs on escaped text; URL capture allows one level of balanced parens.
const inline = (text) => {
let t = escapeHtml(text);
// images: ![alt](url) or ![alt](url "title")
t = t.replace(/!\[([^\]]*)\]\(((?:[^()\s]|\([^)\s]*\))*)(?:\s+"([^"]*)")?\)/g,
(m, alt, url, title) => {
const tAttr = title ? ` title="${title}"` : "";
return `<img src="${sanitizeUrl(url)}" alt="${alt}"${tAttr}>`;
});
// links: [text](url) or [text](url "title")
t = t.replace(/\[([^\]]+)\]\(((?:[^()\s]|\([^)\s]*\))*)(?:\s+"([^"]*)")?\)/g,
(m, txt, url, title) => {
const tAttr = title ? ` title="${title}"` : "";
return `<a href="${sanitizeUrl(url)}" target="_blank" rel="noopener noreferrer"${tAttr}>${txt}</a>`;
});
// bold: **text** or __text__
t = t.replace(/\*\*([^*]+?)\*\*/g, "<strong>$1</strong>");
t = t.replace(/__([^_]+?)__/g, "<strong>$1</strong>");
// strikethrough: ~~text~~
t = t.replace(/~~([^~]+?)~~/g, "<del>$1</del>");
// italic: *text* (avoid *** by requiring non-star borders)
t = t.replace(/(^|[^*])\*([^*]+?)\*(?!\*)/g, "$1<em>$2</em>");
// italic: _text_ (skip word-internal underscores like file_name)
t = t.replace(/(^|[^_\w])_([^_]+?)_(?!\w)/g, "$1<em>$2</em>");
return t;
};
@ -94,19 +71,16 @@ via innerHTML. Exposes window.renderMarkdown(text) -> html.
const out = [];
const n = lines.length;
let i = 0;
let taskSeq = 0; // ordinal of rendered task items, stable across code-block stashing
let taskSeq = 0; // stable across code-block stashing
const isToken = (s) => /^\u0000\d+\u0000$/.test(s);
while (i < n) {
const line = lines[i];
// Blank line separates blocks.
if (/^\s*$/.test(line)) { i++; continue; }
// A stashed block (e.g. a fenced code block) sitting on its own line.
if (isToken(line)) { out.push(line); i++; continue; }
// ATX heading: # Title (optional closing hashes)
const h = line.match(/^(#{1,6})\s+(.*?)(?:\s+#{1,6})?$/);
if (h) {
const lvl = h[1].length;
@ -114,13 +88,11 @@ via innerHTML. Exposes window.renderMarkdown(text) -> html.
i++; continue;
}
// Horizontal rule: --- / *** / ___
if (/^\s*(-{3,}|\*{3,}|_{3,})\s*$/.test(line)) {
out.push("<hr>");
i++; continue;
}
// Blockquote: > ...
if (/^>{1}\s?/.test(line)) {
const quote = [];
while (i < n && /^>{1}\s?/.test(lines[i])) {
@ -131,7 +103,6 @@ via innerHTML. Exposes window.renderMarkdown(text) -> html.
continue;
}
// Unordered list: - / * / + (supports task lists: - [ ] / - [x])
if (/^\s*[-*+]\s+/.test(line)) {
const items = [];
while (i < n) {
@ -149,7 +120,7 @@ via innerHTML. Exposes window.renderMarkdown(text) -> html.
}
i++; continue;
}
// Lazy continuation (indented) of the previous item.
// lazy continuation of the previous item
if (/^\s+\S/.test(lines[i]) && items.length) {
items[items.length - 1] += "<br>" + inline(lines[i].trim());
i++; continue;
@ -160,7 +131,6 @@ via innerHTML. Exposes window.renderMarkdown(text) -> html.
continue;
}
// Ordered list: 1.
if (/^\s*\d+\.\s+/.test(line)) {
const items = [];
while (i < n) {
@ -176,7 +146,6 @@ via innerHTML. Exposes window.renderMarkdown(text) -> html.
continue;
}
// Paragraph: gather consecutive lines until a block boundary.
const para = [line];
i++;
while (i < n) {
@ -195,7 +164,6 @@ via innerHTML. Exposes window.renderMarkdown(text) -> html.
}
let html = out.join("\n");
// Restore stashed HTML.
html = html.replace(/\u0000(\d+)\u0000/g, (m, idx) => stash[+idx] || "");
return html;
}

File diff suppressed because it is too large Load Diff

View File

@ -286,7 +286,6 @@ const themes = [
{ "color": "blue", "score": 2220, "title": "GreysAnatomy by Emberli", "exports": { "disable_color_overlay": true, "gradient_cards": false, "dark_mode": true, "dark_preset": { "background-0": "#4a71fc", "background-1": "#080821", "background-2": "#080821", "borders": "#f7f7f8", "links": "#121131", "sidebar": "#080821", "sidebar-text": "#fcfcfd", "text-0": "#fcfcfc", "text-1": "#ffffff", "text-2": "#fafafa" }, "custom_cards": ["https://i.pinimg.com/564x/98/4b/ea/984beac6a1c618358560e08d237c10ff.jpg", "https://i.pinimg.com/564x/5e/92/f7/5e92f7aaf90b3283725b5ea64bf229a4.jpg", "https://i.pinimg.com/564x/fd/60/e2/fd60e2c0e20c854d3a23d53674cd2792.jpg", "https://i.pinimg.com/564x/0d/67/b6/0d67b612c91d3b2a1655827fb2c34e85.jpg", "https://i.pinimg.com/564x/5c/cd/5b/5ccd5b37d890a333f76d9622855249c7.jpg", "https://i.pinimg.com/564x/66/23/14/662314b9e24dd7f024c00f5dbae61d12.jpg", "https://i.pinimg.com/564x/d9/87/76/d987760a478c0112d4110cdc904d2345.jpg", "https://i.pinimg.com/736x/73/92/73/7392738c606475fb3801006e96913427.jpg"], "card_colors": ["#8f0083"], "custom_font": { "family": "'Caveat'", "link": "Caveat:wght@400;700" } }, "preview": "https://i.pinimg.com/564x/66/23/14/662314b9e24dd7f024c00f5dbae61d12.jpg" },
{ "color": "beige", "score": 4340, "title": "beigestudy by nowshin", "exports": { "disable_color_overlay": true, "gradient_cards": false, "dark_mode": true, "dark_preset": { "background-0": "#fff8f0", "background-1": "#e8ccb5", "background-2": "#fee1e1", "borders": "#b48e7e", "links": "#ffcccc", "sidebar": "#f0d6d6", "sidebar-text": "#704c2e", "text-0": "#472610", "text-1": "#481d0f", "text-2": "#ffcccc" }, "custom_cards": ["https://i.pinimg.com/736x/87/fc/8c/87fc8ca9428caff232f37bd9ef547aad.jpg", "https://i.pinimg.com/originals/14/f6/57/14f657847d5085bb944ce9df6e25f7c3.jpg", "https://i.pinimg.com/originals/dd/07/87/dd078735318110132bc02e22be16c4b7.jpg", "https://i.pinimg.com/736x/82/0d/7e/820d7edf5c4ae7d29e54772eee33c92d.jpg", "https://i.pinimg.com/originals/ce/67/aa/ce67aaa41da4c60eca91e30547499267.jpg", "https://i.pinimg.com/564x/5a/23/53/5a2353d4d88067869c5aa6a6cc7c2882.jpg", "https://i.pinimg.com/564x/7a/98/13/7a9813601d213722fcdb2c4d41dfed85.jpg", "https://i.pinimg.com/564x/07/47/52/074752696090540ff352a4c1196b6107.jpg", "https://i.pinimg.com/564x/9f/90/be/9f90be69e82f94a776bb58033fc7ed57.jpg"], "card_colors": ["#d9b99b"], "custom_font": { "family": "'Comfortaa'", "link": "Comfortaa:wght@400;700" } }, "preview": "https://i.pinimg.com/564x/5a/23/53/5a2353d4d88067869c5aa6a6cc7c2882.jpg" },
{ "color": "pink", "score": 4440, "title": "BerryStickO by EcstasyCheese", "exports": { "disable_color_overlay": true, "gradient_cards": false, "dark_mode": true, "dark_preset": { "background-0": "#feecf0", "background-1": "#ffffff", "background-2": "#ca1c47", "borders": "#e56182", "links": "#ca1c47", "sidebar": "linear-gradient(#e56182, #f4c0cd)", "sidebar-text": "#ffffff", "text-0": "#ca1c47", "text-1": "#e56182", "text-2": "#000000" }, "custom_cards": ["https://preview.redd.it/strawberry-sticko-v1-pics-for-canvasrefined-v0-94b9j5sn92hd1.png?width=528&format=png&auto=webp&s=bcb9064929f077dac8ab9755b8854d0cb6170847", "https://preview.redd.it/strawberry-sticko-v1-pics-for-canvasrefined-v0-svbdb5sn92hd1.png?width=528&format=png&auto=webp&s=4ff3ca5aceae9fe2937550ea4de69d03fbbd32a8", "https://preview.redd.it/strawberry-sticko-v1-pics-for-canvasrefined-v0-ro8no9sn92hd1.png?width=528&format=png&auto=webp&s=222f2855a7508be4642fb3e0fd10d96dc942e7e2", "https://preview.redd.it/strawberry-sticko-v1-pics-for-canvasrefined-v0-wrwoh6sn92hd1.png?width=528&format=png&auto=webp&s=e331b7ac992f14b49782b512452393546ee2164a", "https://preview.redd.it/strawberry-sticko-v1-pics-for-canvasrefined-v0-cacj2asn92hd1.png?width=528&format=png&auto=webp&s=a11d3f39c94cafb6e956b58220419c6da4448416", "https://preview.redd.it/strawberry-sticko-v1-pics-for-canvasrefined-v0-dzmi19sn92hd1.png?width=528&format=png&auto=webp&s=f59d7aa5aaacc6e4d184e7dd014e8eded1cfde9f", "https://preview.redd.it/strawberry-sticko-v1-pics-for-canvasrefined-v0-l6yyr7sn92hd1.png?width=528&format=png&auto=webp&s=7fd269561ef552feab8df80c1ddc830c3330e28a", "https://preview.redd.it/strawberry-sticko-v1-pics-for-canvasrefined-v0-on4fi3sn92hd1.png?width=528&format=png&auto=webp&s=da34348328014ef38a1caca5f8b8f141c4508e3f"], "card_colors": ["#ca1c47"], "custom_font": { "family": "'gochi hand'", "link": "Gochi+Hand:wght@400;700" } }, "preview": "https://preview.redd.it/strawberry-sticko-v1-pics-for-canvasrefined-v0-svbdb5sn92hd1.png?width=528&format=png&auto=webp&s=4ff3ca5aceae9fe2937550ea4de69d03fbbd32a8" },
//{ "title": "Stray kids by Saishee", "exports": { "disable_color_overlay": true, "gradient_cards": false, "dark_mode": true, "dark_preset": { "background-0": "#0f0f0f", "background-1": "#0c0c0c", "background-2": "#211c1c", "borders": "#1e1e1e", "links": "#c6d7d1", "sidebar": "#0c0c0c", "sidebar-text": "#f5f5f5", "text-0": "#edc4c4", "text-1": "#e2e2e2", "text-2": "#5b5757" }, "custom_cards": ["https://i.pinimg.com/474x/6a/a4/32/6aa4326db14cfc001f926442bec125d5.jpg", "https://i.pinimg.com/474x/b3/7a/9c/b37a9c6857416ccf33bec2c68bcc94b5.jpg", "https://i.pinimg.com/564x/76/a3/fb/76a3fb5cc7caddfa3239fc5a32cb1dee.jpg", "https://i.pinimg.com/474x/0a/e3/23/0ae323e8bd7934d8441816499d8e7359.jpg", "https://i.pinimg.com/474x/69/28/c8/6928c8c7bf0cadbd4369d14f46b6c2d8.jpg", "https://i.pinimg.com/474x/4d/57/a9/4d57a99053f87872a7f53d6cdf1f65de.jpg", "https://i.pinimg.com/474x/e4/52/5a/e4525a3aceb0656b6124f7f1e5d477d6.jpg", "https://i.pinimg.com/474x/dc/00/41/dc0041b2a2bc234837a38aef21f3ccd2.jpg", "https://i.pinimg.com/474x/69/c7/7e/69c77ef8a3e9017f4a956535b0e6eb4f.jpg"], "card_colors": ["#c6d7d1"], "custom_font": { "family": "'Playfair Display'", "link": "Playfair+Display:wght@400;700" } }, "preview": "https://i.pinimg.com/474x/69/c7/7e/69c77ef8a3e9017f4a956535b0e6eb4f.jpg" },
{ "color": "beige", "score": 3330, "title": "Fantasy by Miranda", "exports": { "disable_color_overlay": true, "gradient_cards": false, "dark_mode": true, "dark_preset": { "background-0": "#E1D8C4", "background-1": "#", "background-2": "#", "borders": "#3d251e", "links": "#d28584", "sidebar": "linear-gradient(#d28584c7, #000000c7), center url(\"https://i.pinimg.com/564x/32/03/2f/32032f56d1513a97a5804c09739545f9.jpg\")", "sidebar-text": "#f5f5f5", "text-0": "#3d251e", "text-1": "#3d251e", "text-2": "#3d251e" }, "custom_cards": ["https://i.pinimg.com/736x/2b/22/c6/2b22c64160677cb97fa36e8012f07ddc.jpg", "https://i.pinimg.com/736x/48/ef/ed/48efedc6e53fb27170b52a76b73b7204.jpg", "https://i.pinimg.com/564x/85/4d/7b/854d7bd85ae1bef392c80c7e3f01a419.jpg", "https://i.pinimg.com/564x/59/e3/a7/59e3a7e93e7354878238857f3c070f6e.jpg", "https://i.pinimg.com/564x/32/03/2f/32032f56d1513a97a5804c09739545f9.jpg", "https://i.pinimg.com/564x/60/37/d8/6037d838a415a126ac091ca733646bca.jpg", "https://i.pinimg.com/736x/87/e4/ec/87e4ecc23258fac19b6b00bdcef73939.jpg", "https://i.pinimg.com/564x/39/3e/0e/393e0eacc03642dd8fa663f230f5164b.jpg", "https://i.pinimg.com/564x/0c/79/c9/0c79c9d5ea846b1e79fe2db31f76d82e.jpg", "https://i.pinimg.com/564x/ff/b0/17/ffb017b914b5acd29afc18251dab18dd.jpg", "https://i.pinimg.com/564x/d5/38/54/d53854ba4b45d6e8ab7862319a03bdf5.jpg"], "card_colors": ["#3d251e"], "custom_font": { "family": "'Nanum Myeongjo'", "link": "Nanum+Myeongjo:wght@400;700" } }, "preview": "https://i.pinimg.com/564x/39/3e/0e/393e0eacc03642dd8fa663f230f5164b.jpg" },
{ "color": "red", "score": 4430, "title": "cherry by elizabeth", "exports": { "disable_color_overlay": true, "gradient_cards": false, "dark_mode": true, "dark_preset": { "background-0": "#963131", "background-1": "#5a2626", "background-2": "", "borders": "", "links": "", "sidebar": "#5a2626", "sidebar-text": "#eddbc2", "text-0": "#eddbc2", "text-1": "#eddbc2", "text-2": "#eddbc2" }, "custom_cards": ["https://i.pinimg.com/564x/b5/11/75/b51175545c2af654df242afa0d514025.jpg", "https://i.pinimg.com/736x/f9/6a/6a/f96a6a6302269e92a9d345ce4c54646b.jpg", "https://i.pinimg.com/564x/ac/41/e9/ac41e9ec5ff2d9d95ede13ba33b77235.jpg", "https://i.pinimg.com/736x/6b/7c/1b/6b7c1b108902be1deb72e31c7c7020e4.jpg", "https://i.pinimg.com/736x/79/88/f4/7988f47d7903bd6aa4d8f366cdddeaf8.jpg", "https://i.pinimg.com/564x/97/2d/f7/972df785c3f9f1e0d9b93615d2520328.jpg", "https://i.pinimg.com/736x/36/b0/0b/36b00bf63da23229daab0a82be9bd7fe.jpg"], "card_colors": ["#bb3b38", "#008400", "#5a2626", "#5a2626", "#5a2626", "#5a2626", "#5a2626", "#bb3b38"], "custom_font": { "family": "'Rubik'", "link": "Rubik:wght@400;700" } }, "preview": "https://i.pinimg.com/564x/b5/11/75/b51175545c2af654df242afa0d514025.jpg" },
{ "color": "blue", "score": 4430, "title": "blueflower by Rosey", "exports": { "disable_color_overlay": true, "gradient_cards": false, "dark_mode": true, "dark_preset": { "background-0": "#154360", "background-1": "#2874A6", "background-2": "#3498DB", "borders": "#85C1E9", "links": "#AED6F1", "sidebar": "linear-gradient(#000000c7, #2874A6c7), center url(\"https://i.etsystatic.com/16700126/r/il/545b20/4708047920/il_570xN.4708047920_qf65.jpg\")", "sidebar-text": "#AED6F1", "text-0": "#AED6F1", "text-1": "#FEF5E7", "text-2": "#adb1aa" }, "custom_cards": ["https://s.widget-club.com/images/YyiR86zpwIMIfrCZoSs4ulVD9RF3/79fcde271c47643ed27611be0763ee86/1c4daad923d3841e6e173880fe0a76f9.jpg?q=70&w=500", "https://encrypted-tbn0.gstatic.com/images?q=tbn:ANd9GcRzXzmG-BLY3dhF10J09EOlPRimImR129he2OoIIH1feaerKjMG9tldPHB6MmBFOc_eteM&usqp=CAU", "https://cdn.shopify.com/s/files/1/1034/3311/files/hydrangea-flowers-in-the-garden-picture-id927499422_1024x1024.jpg?v=1578384074", "https://encrypted-tbn0.gstatic.com/images?q=tbn:ANd9GcQAqC_Vlm2BYRpL1hZloGinds0TuLQ-D6UspWsOciaVcu3UlB3gBJfeDNhfHR0GEqsprJE&usqp=CAU", "https://t4.ftcdn.net/jpg/07/90/41/99/360_F_790419905_ksWKSHZJlugHfAcYgEAa5iQR4oVjxtoQ.jpg", "https://encrypted-tbn0.gstatic.com/images?q=tbn:ANd9GcTy9Pnbaz605B-Rm7eeWzbptF6qyay7KEaovA&s", "https://as1.ftcdn.net/v2/jpg/06/08/69/46/1000_F_608694688_MuVFL7aLPz5O4zXMJ1NO17PRWHCoiyzG.jpg", "https://i.pinimg.com/474x/2d/d4/7e/2dd47e2846d4b02f7dcafd4a4895b14f.jpg", "https://static.vecteezy.com/system/resources/thumbnails/033/694/873/small/detailed-close-up-of-cornflower-petals-ai-generative-photo.jpg", "https://encrypted-tbn0.gstatic.com/images?q=tbn:ANd9GcSs0epOLuYjq1u0hYZuyOWdO-X5g47qmBVZ85BIfcKojUnoo3a7Ze3_XWQZX3byilza7mQ&usqp=CAU", "https://encrypted-tbn0.gstatic.com/images?q=tbn:ANd9GcRrhsrdGgRyasIP5vpf_PVWByqJUaTdhRW7s8KV_9qc7VexL3iWfcwK7m1aUaEI2qX07MU&usqp=CAU", "https://encrypted-tbn0.gstatic.com/images?q=tbn:ANd9GcTTo5uvFz2xXusUABOLSs6y4SjNeqC81-VfaoABMyWzSuWyjATrAbIgJRtYcOfUaZjQ_to&usqp=CAU", "https://encrypted-tbn0.gstatic.com/images?q=tbn:ANd9GcQl9zD9sh2zNumtsFXuNs-eKoSIQ6g34fMH8VbKFEzu8Q2ht3s9T-XztRpXZXm3MstRJsw&usqp=CAU", "https://img.freepik.com/premium-photo/blue-flowers-wallpaper-iphone-is-best-high-definition-iphone-wallpaper-you-can-make-this-wallpaper-your-iphone-x-backgrounds-mobile-screensaver-ipad-lock-screen-iphone-blue_901003-2989.jpg?w=360", "https://encrypted-tbn0.gstatic.com/images?q=tbn:ANd9GcQ87NWgBHFJGpxiuIlnVZc9bDJkTCPuL3OQTg&s"], "card_colors": ["#AED6F1"], "custom_font": { "family": "'Corben'", "link": "Corben:wght@400;700" } }, "preview": "https://encrypted-tbn0.gstatic.com/images?q=tbn:ANd9GcTTo5uvFz2xXusUABOLSs6y4SjNeqC81-VfaoABMyWzSuWyjATrAbIgJRtYcOfUaZjQ_to&usqp=CAU" },
@ -434,36 +433,4 @@ const themes = [
/*
{ "title": "Motivational by Adrianna", "exports": { "disable_color_overlay": true, "gradient_cards": false, "dark_mode": true, "dark_preset": { "background-0": "#202020", "background-1": "#2e2e2e", "background-2": "#4e4e4e", "borders": "#404040", "links": "#56Caf0", "sidebar": "#2e2e2e", "sidebar-text": "#f5f5f5", "text-0": "#f5f5f5", "text-1": "#e2e2e2", "text-2": "#ababab" }, "custom_cards": ["https://i.pinimg.com/474x/1d/3a/0e/1d3a0e1b3543d873cf8de35a2911c03f.jpg", "https://i.pinimg.com/474x/dd/e8/27/dde8279847d6f508b426a094a5aac28a.jpg", "https://i.pinimg.com/474x/ee/b4/60/eeb4601e423baccb5a8e5f091ec8cc9f.jpg", "https://i.pinimg.com/474x/9a/9f/e3/9a9fe35de7a80fb8cc3079167c2b01a8.jpg", "https://i.pinimg.com/474x/eb/37/af/eb37afabc5d1f0138c7ba5a1810158ea.jpg", "https://i.pinimg.com/474x/63/66/dd/6366dd0b47728a60f1d81262ab618724.jpg", "https://i.pinimg.com/474x/13/47/96/13479630adf41bc42c4b542590282526.jpg"], "card_colors": ["#000000"], "custom_font": { "family": "'Open Sans'", "link": "Open+Sans:wght@400;700" } }, "preview": "https://i.pinimg.com/474x/1d/3a/0e/1d3a0e1b3543d873cf8de35a2911c03f.jpg" },
{ "title": "Chainsaw by Mykol", "exports": { "disable_color_overlay": true, "gradient_cards": false, "dark_mode": true, "dark_preset": { "background-0": "#0f0f0f", "background-1": "#0c0c0c", "background-2": "#141414", "borders": "#1e1e1e", "links": "#f49e0b", "sidebar": "#0c0c0c", "sidebar-text": "#f5f5f5", "text-0": "#f5f5f5", "text-1": "#e2e2e2", "text-2": "#ababab" }, "custom_cards": ["https://pbs.twimg.com/media/FjCyGhvXwAAjFqn.jpg", "https://w.wallhaven.cc/full/dp/wallhaven-dpvd2g.jpg", "https://i.pinimg.com/originals/31/3e/57/313e570a0cf1493790669461d65b7137.jpg", "https://i.ytimg.com/vi/5SdHEv04Wic/maxresdefault.jpg", "https://pbs.twimg.com/media/E5htXu2WEAM4WiL.jpg"], "card_colors": ["#e36d0d"], "custom_font": { "family": "'Rubik'", "link": "Rubik:wght@400;700" } }, "preview": "https://i.pinimg.com/originals/31/3e/57/313e570a0cf1493790669461d65b7137.jpg" },
{ "title": "LeonK by BlancaC", "exports": { "disable_color_overlay": false, "gradient_cards": false, "dark_mode": true, "dark_preset": { "background-0": "#232425", "background-1": "#1e1e1e", "background-2": "#262626", "borders": "#4e1313", "links": "#e255b5", "sidebar": "linear-gradient(#b88ea5c7, #6b0a3ec7), center url(\"https://i.pinimg.com/736x/71/a7/b1/71a7b19b26616a7e54c802b8ae898080.jpg\")", "sidebar-text": "#fdd3e7", "text-0": "#f5f5f5", "text-1": "#e2e2e2", "text-2": "#ababab" }, "custom_cards": ["https://i.pinimg.com/736x/d4/a1/6e/d4a16ee82c8e45ffbc03611808ec3202.jpg", "https://i.pinimg.com/474x/ab/fc/50/abfc50beea6f05c428a0a42c415d1a2b.jpg", "https://i.pinimg.com/736x/11/d9/22/11d92290bd92f6719e687f86a734db3d.jpg", "https://game.capcom.com/residentevil/pc/img/umbrella/20230324/utu1_31-1.jpg", "https://cdn.vox-cdn.com/thumbor/Og1IT6M5rO4C_z3eIodSjBB6P-o=/0x0:2854x1560/1200x0/filters:focal(0x0:2854x1560):no_upscale()/cdn.vox-cdn.com/uploads/chorus_asset/file/24774139/5.Leon.Culp.jpg", "https://i.pinimg.com/236x/07/08/80/0708805a022e79d7dbd8077bba877a8d.jpg", "https://www.svg.com/img/gallery/the-worst-things-resident-evils-leon-kennedy-has-ever-done/intro-1657287618.jpg", "https://preview.redd.it/leon-kennedy-is-absurdly-attractive-in-resident-evil-4-v0-24o386br63ta1.jpg?width=640&crop=smart&auto=webp&s=29215993db324eec1a0c3153e6d442a2eca2d463", "https://i.pinimg.com/736x/3a/d0/e0/3ad0e09f1c249f5ea858564036d4ba6e.jpg"], "card_colors": ["#ff0a54", "#ff5c8a", "#ff85a1", "#ff99ac", "#fbb1bd", "#ff0a54", "#ff5c8a", "#ff85a1", "#ff99ac"], "custom_font": { "family": "'Tektur'", "link": "Tektur:wght@400;700" } }, "preview": "https://i.pinimg.com/236x/07/08/80/0708805a022e79d7dbd8077bba877a8d.jpg" },
{ "title": "Forest by Alia", "exports": { "disable_color_overlay": true, "gradient_cards": false, "dark_mode": true, "dark_preset": { "background-0": "#272727", "background-1": "#353535", "background-2": "#404040", "borders": "#454545", "links": "#56Caf0", "sidebar": "#353535", "sidebar-text": "#f5f5f5", "text-0": "#f5f5f5", "text-1": "#e2e2e2", "text-2": "#ababab" }, "custom_cards": ["https://i.pinimg.com/originals/aa/33/d5/aa33d5bf71e6d8fdb050b1e104b7c437.gif", "https://i.pinimg.com/originals/eb/54/d4/eb54d4191a91f9ff3c2f9a198471136b.gif", "https://i.pinimg.com/originals/3b/a0/87/3ba0876e7f971ba78fb3b8b329003576.gif", "https://i.pinimg.com/originals/aa/33/d5/aa33d5bf71e6d8fdb050b1e104b7c437.gif"], "card_colors": ["#124229", "#3a4c40", "#b7b7a4"], "custom_font": { "family": "'Tektur'", "link": "Tektur:wght@400;700" } }, "preview": "https://encrypted-tbn2.gstatic.com/images?q=tbn:ANd9GcQ-1LXVIfQ3A3B1QcRuF8DVHF13ekVFBrvd8MDD0eYPodDbVMcS" },
{ "title": "Neon by Gabriel", "exports": { "disable_color_overlay": true, "gradient_cards": false, "dark_mode": true, "dark_preset": { "background-0": "#161616", "background-1": "#56c2bb", "background-2": "#4be285", "borders": "#00d0fa", "links": "#ff80ca", "sidebar": "linear-gradient(#6bd3e1, #fe6794)", "sidebar-text": "#f5f5f5", "text-0": "#9ae5fe", "text-1": "#ff7ac8", "text-2": "#70ffb5" }, "custom_cards": ["https://encrypted-tbn0.gstatic.com/images?q=tbn:ANd9GcRTwmWMKqKcq9-amzPxhVRVp9nBCk2_NmpK_g"], "card_colors": ["#975bc9"], "custom_font": { "family": "'Nova Script'", "link": "Nova Script:wght@400;700" } }, "preview": "https://encrypted-tbn0.gstatic.com/images?q=tbn:ANd9GcRTwmWMKqKcq9-amzPxhVRVp9nBCk2_NmpK_g" },
{ "title": "Gloomy by Simonii", "exports": { "disable_color_overlay": true, "gradient_cards": false, "dark_mode": true, "dark_preset": { "background-0": "#272625", "background-1": "#282624", "background-2": "#1e1a1a", "borders": "#423e3e", "links": "#ebe0cb", "sidebar": "linear-gradient(#ffeed6c7, #000000c7), center url(\"https://i.imgur.com/RnMvKQi.png\")", "sidebar-text": "#2a1818", "text-0": "#ffffff", "text-1": "#d3c5c5", "text-2": "#f7cfcf" }, "custom_cards": ["https://i.pinimg.com/564x/e1/1b/9a/e11b9aafa1255e0ce3e3acedb1dc3b33.jpg", "https://i.pinimg.com/736x/0e/d6/49/0ed649ba78863b1fe7f98c2cc653c973.jpg", "https://i.pinimg.com/736x/82/c0/7a/82c07a11def29584bbc6889bebecdf8a.jpg", "https://i.pinimg.com/564x/13/75/0f/13750f212f7a3a6af876d74676048a35.jpg", "https://i.pinimg.com/564x/26/6c/80/266c802a6bdff40e22eb7801bd8c5907.jpg", "https://i.pinimg.com/564x/c6/5c/e5/c65ce551b92d7145950b3537405af2e1.jpg", "https://i.pinimg.com/564x/9f/4a/20/9f4a20e94c9c3a07497ba11d31a43a19.jpg", "https://i.pinimg.com/564x/82/80/91/828091620792f6bfb4ffabb4806d996d.jpg", "https://i.pinimg.com/564x/4d/52/8a/4d528a80011c92f3f075d05bd90c706e.jpg", "https://i.pinimg.com/564x/b1/d6/dd/b1d6dde245d5dff3abcdbc127fc6d68a.jpg", "https://i.pinimg.com/564x/40/fd/9e/40fd9ebcbdcc6ba289f8e991d74de01d.jpg", "https://i.pinimg.com/564x/64/cf/05/64cf059ba4e9bbb9b94aced1dc85e570.jpg"], "card_colors": ["#34fecb"], "custom_font": { "family": "'Nanum Myeongjo'", "link": "Nanum+Myeongjo:wght@400;700" } }, "preview": "https://i.pinimg.com/564x/4d/52/8a/4d528a80011c92f3f075d05bd90c706e.jpg" },
{ "title": "Vergil by nickolas", "exports": { "disable_color_overlay": true, "gradient_cards": false, "dark_mode": true, "dark_preset": { "background-0": "#101010", "background-1": "#121212", "background-2": "#1a1a1a", "borders": "#272727", "links": "#db334c", "sidebar": "#121212", "sidebar-text": "#f5f5f5", "text-0": "#f5f5f5", "text-1": "#e2e2e2", "text-2": "#ababab" }, "custom_cards": ["https://media.giphy.com/media/v1.Y2lkPTc5MGI3NjExMHgwYzd2eXU3cnc5ajY5bDZuODh6aGtzNnI4NG0yYzNxMDhsdTNndCZlcD12MV9naWZzX3NlYXJjaCZjdD1n/ZRouJhQpbhPzTJ2eBU/giphy.gif", "https://media.giphy.com/media/uFxXhqkaGuhvzlOXNb/giphy.gif?cid=790b76110x0c7vyu7rw9j69l6n88zhks6r84m2c3q08lu3gt&ep=v1_gifs_search&rid=giphy.gif&ct=g", "https://media.giphy.com/media/9VtZa3W3UjmQgFTY4I/giphy.gif?cid=790b76110x0c7vyu7rw9j69l6n88zhks6r84m2c3q08lu3gt&ep=v1_gifs_search&rid=giphy.gif&ct=g", "https://media.giphy.com/media/KzQ8OChBq9EBSMf1f7/giphy.gif?cid=790b7611bhvvqwfl4oarmtqijtrb8zw4qx24bkhh5hxeg0wq&ep=v1_gifs_search&rid=giphy.gif&ct=g", "https://media.giphy.com/media/n1DsSMIPUO5TfUcpML/giphy.gif?cid=790b7611bhvvqwfl4oarmtqijtrb8zw4qx24bkhh5hxeg0wq&ep=v1_gifs_search&rid=giphy.gif&ct=g"], "card_colors": ["#c71f37"], "custom_font": { "family": "'Comfortaa'", "link": "Comfortaa:wght@400;700" } }, "preview": "https://i.pinimg.com/236x/90/0a/d6/900ad68e98b661ed72d9260639bd06b0.jpg" },
{ "title": "Folklore by Amy", "exports": { "disable_color_overlay": true, "gradient_cards": false, "dark_mode": true, "dark_preset": { "background-0": "#202020", "background-1": "#2e2e2e", "background-2": "#4e4e4e", "borders": "#404040", "links": "#050505", "sidebar": "#2e2e2e", "sidebar-text": "#f5f5f5", "text-0": "#f5f5f5", "text-1": "#e2e2e2", "text-2": "#ababab" }, "custom_cards": ["https://i.pinimg.com/564x/3a/92/15/3a921570cd8d200a36b596f169c86c9e.jpg", "https://i.pinimg.com/236x/74/31/e7/7431e7f2739bed4af436cb13909992ae.jpg", "https://i.pinimg.com/564x/e4/73/7f/e4737f38dca2411bd4e4e0ce90332b2d.jpg", "https://i.pinimg.com/564x/c6/40/70/c640701406c3b0c82897622a25336240.jpg", "https://i.pinimg.com/564x/47/4f/28/474f2814fd9e3d33db4a02cb477fc735.jpg", "https://i.pinimg.com/564x/c1/bf/34/c1bf34a8e0a257eb24727de4930b1797.jpg"], "card_colors": ["#e7e6f7", "#e3d0d8", "#aea3b0", "#827081", "#c6d2ed", "#e7e6f7", "#e3d0d8", "#aea3b0", "#827081", "#c6d2ed", "#e7e6f7"], "custom_font": { "family": "'https'", "link": "https:wght@400;700" } }, "preview": "https://i.pinimg.com/564x/3a/92/15/3a921570cd8d200a36b596f169c86c9e.jpg" },
{ "title": "Pagani by Samuel", "exports": { "disable_color_overlay": true, "gradient_cards": false, "dark_mode": true, "dark_preset": { "background-0": "#292929", "background-1": "#4f4f4f", "background-2": "#757575", "borders": "#000000", "links": "#498092", "sidebar": "linear-gradient(#a8a4a4c7, #4d4d4dc7), center url(\"https://static1.hotcarsimages.com/wordpress/wp-content/uploads/2019/08/Pagani-Zonda-Cinque.jpg\")", "sidebar-text": "#f5f5f5", "text-0": "#f5f5f5", "text-1": "#c2c2c2", "text-2": "#ababab" }, "custom_cards": ["https://cdn.carbuzz.com/gallery-images/840x560/274000/800/274822.jpg", "https://upload.wikimedia.org/wikipedia/commons/thumb/1/18/Pagani_Utopia.jpg/1200px-Pagani_Utopia.jpg", "https://www.motortrend.com/uploads/2021/09/Pagani-Huayra-BC-Roadster-02-1.jpg", "https://www.thesupercarblog.com/wp-content/uploads/2024/01/Worlds-First-Pagani-Imola-Roadster-delivery-Miami-1.jpg", "https://www.topgear.com/sites/default/files/2021/08/2010-Pagani-Zonda-R-Evolution-_0.jpg"], "card_colors": ["#808080"], "custom_font": { "family": "'Arimo'", "link": "Arimo:wght@400;700" } }, "preview": "https://cdn.carbuzz.com/gallery-images/840x560/274000/800/274822.jpg" },
{ "title": "ErasCollage by Mischa", "exports": { "disable_color_overlay": true, "gradient_cards": false, "dark_mode": true, "dark_preset": { "background-0": "#242424", "background-1": "#10100f", "background-2": "#c0c1be", "borders": "#b7b4b4", "links": "#d5ebfa", "sidebar": "linear-gradient(#000000c7, #fffafac7), center url(\"https://i.pinimg.com/564x/f5/c8/90/f5c890a64b6292cda6d4a3d0ae34786f.jpg\")", "sidebar-text": "#f5f5f5", "text-0": "#d5ebfa", "text-1": "#d5ebfa", "text-2": "#d5ebfa" }, "custom_cards": ["https://i.pinimg.com/564x/7c/49/da/7c49da504872a5fccfe6be08e94febda.jpg", "https://i.pinimg.com/564x/c1/0e/20/c10e20f5939dab75acd0fb0f62b34802.jpg", "https://i.pinimg.com/564x/95/19/50/951950ff42de2d14e9903385b6939d90.jpg", "https://i.pinimg.com/564x/9a/a7/60/9aa7602bd830b39782e0b00b8c83bdf3.jpg", "https://i.pinimg.com/736x/34/5d/7b/345d7b6cc57bbfef5c67eb6856c384c4.jpg", "https://i.pinimg.com/564x/07/48/3a/07483a17eb75ce865224f6fc32bfa088.jpg", "https://i.pinimg.com/564x/39/14/58/3914582877119d1083ab03110d35e7a6.jpg", "https://i.pinimg.com/564x/6b/44/ff/6b44ff3676d1258ce1ce7c6037d28a2d.jpg", "https://i.pinimg.com/564x/07/87/29/0787291b871e258b93ed5d450d3f1335.jpg", "https://i.pinimg.com/564x/92/60/0c/92600cc851649e783915a9282cb0ed5f.jpg", "https://i.pinimg.com/564x/d7/78/a0/d778a0bbe4f2b6cc1f96aaa933e4dc8c.jpg", "https://i.pinimg.com/564x/00/58/8f/00588f21bb0eeb306e7003bad7b9558f.jpg"], "card_colors": [], "custom_font": { "family": "'Inconsolata'", "link": "Inconsolata:wght@400;700" } }, "preview": "https://i.pinimg.com/564x/07/48/3a/07483a17eb75ce865224f6fc32bfa088.jpg" },
{ "title": "MoonKnight by Noor", "exports": { "disable_color_overlay": true, "gradient_cards": false, "dark_mode": true, "dark_preset": { "background-0": "#212121", "background-1": "#2e2e2e", "background-2": "#4e4e4e", "borders": "#404040", "links": "#a9a793", "sidebar": "#171717", "sidebar-text": "#f5f5f5", "text-0": "#f5f5f5", "text-1": "#e2e2e2", "text-2": "#ababab" }, "custom_cards": ["https://i.pinimg.com/564x/35/58/0c/35580ceb64d50bc9c7f924ba26b6a7a4.jpg", "https://i.pinimg.com/564x/54/f3/93/54f393577f3f1f7fa96bcd828373573b.jpg", "https://i.pinimg.com/564x/ce/d6/1b/ced61bc49f5bcdf30eb7e71d3f79a980.jpg", "https://i.pinimg.com/564x/1d/cb/13/1dcb13cafea9e8d1267575917e200af2.jpg", "https://i.pinimg.com/564x/b8/b9/dd/b8b9ddb853ee33e649d5d3dfd42b281f.jpg", "https://i.pinimg.com/564x/40/f9/49/40f949cd72bce4d25f271f315926b88a.jpg", "https://i.pinimg.com/564x/4c/2b/44/4c2b44369bc68d1d142e4999679fea8d.jpg", "https://i.pinimg.com/564x/81/21/ab/8121ab3e3a0776e37c477fd00faa15b5.jpg"], "card_colors": ["#888777"], "custom_font": { "family": "'Cinzel'", "link": "Cinzel:wght@400;700" } }, "preview": "https://i.pinimg.com/564x/4c/2b/44/4c2b44369bc68d1d142e4999679fea8d.jpg" },
{ "title": "ItGrl by Pynk", "exports": { "disable_color_overlay": true, "gradient_cards": false, "dark_mode": true, "dark_preset": { "background-0": "#161616", "background-1": "#6f0101", "background-2": "#262626", "borders": "#3c3c3c", "links": "#920202", "sidebar": "linear-gradient(#000000c7, #343232c7), center url(\"https://i.pinimg.com/564x/f8/1c/26/f81c26649e131265ad517212a5c4be91.jpg\")", "sidebar-text": "#9c0202", "text-0": "#ffffff", "text-1": "#ffffff", "text-2": "#ffffff" }, "custom_cards": ["https://i.pinimg.com/564x/a5/ba/00/a5ba00fdffb8bd4754c875001a6c3ec9.jpg", "https://i.pinimg.com/564x/04/c1/e3/04c1e37b8c15686b88c89f5ca32ccde8.jpg", "https://i.pinimg.com/736x/40/75/7e/40757e10a6da0b7d0e14a75e9b450d5f.jpg", "https://i.pinimg.com/564x/45/2e/3f/452e3f6f27f47c31881c08c6cc98677b.jpg", "https://i.pinimg.com/564x/bd/d8/7d/bdd87dc0eb6f8e67aa6c7406be57fa09.jpg", "https://i.pinimg.com/736x/c8/ed/69/c8ed691fb9a62379754aee57b611e655.jpg", "https://i.pinimg.com/564x/e6/b7/13/e6b713ab2884e6c519cfe8c4fd9b0938.jpg", "https://i.pinimg.com/564x/55/fc/94/55fc9403ae83b798943e11d86237dc65.jpg"], "card_colors": ["#e01e37", "#c71f37", "#b21e35", "#a11d33", "#6e1423", "#e01e37", "#c71f37", "#b21e35", "#a11d33"], "custom_font": { "family": "'Cinzel'", "link": "Cinzel:wght@400;700" } }, "preview": "https://i.pinimg.com/564x/a5/ba/00/a5ba00fdffb8bd4754c875001a6c3ec9.jpg" },
{ "title": "Snoopy by AJ", "exports": { "disable_color_overlay": true, "gradient_cards": false, "dark_mode": true, "dark_preset": { "background-0": "#101010", "background-1": "#141414", "background-2": "#1a1a1a", "borders": "#5a6d5c", "links": "#91b196", "sidebar": "#5a6d5c", "sidebar-text": "#f5f5f5", "text-0": "#f5f5f5", "text-1": "#e2e2e2", "text-2": "#ababab" }, "custom_cards": ["https://i.pinimg.com/474x/e7/21/0b/e7210bfd30e17fd4342548d56ca78682.jpg", "https://i.pinimg.com/474x/48/ec/60/48ec6050058d7c29aa363e017dd572b4.jpg", "https://i.pinimg.com/474x/65/5a/f4/655af491cf19894e92e8c602a1e5f721.jpg", "https://i.pinimg.com/474x/9c/c3/86/9cc3866bc8030b15d361ab7ff2e4fd7e.jpg", "https://i.pinimg.com/474x/44/db/d8/44dbd8ce4e41e4d6768c7923fd6e8b09.jpg", "https://i.pinimg.com/474x/b0/1f/f3/b01ff39b649dbe760c8ae1094df98730.jpg", "https://i.pinimg.com/474x/4b/54/62/4b5462b41072c561175924a4a0e5c194.jpg", "https://i.pinimg.com/474x/82/90/1d/82901d12a3e380d3e974bfef719b5919.jpg", "https://i.pinimg.com/474x/d7/91/53/d79153d4c7d8d18f6008e017c013962e.jpg"], "card_colors": ["#91b196"], "custom_font": { "family": "", "link": "" } }, "preview": "https://i.pinimg.com/474x/4b/54/62/4b5462b41072c561175924a4a0e5c194.jpg" },
{ "title": "Ferrari by Vincent", "exports": { "disable_color_overlay": false, "gradient_cards": false, "dark_mode": true, "dark_preset": { "background-0": "#101010", "background-1": "#121212", "background-2": "#1a1a1a", "borders": "#272727", "links": "#d60000", "sidebar": "#121212", "sidebar-text": "#f5f5f5", "text-0": "#f5f5f5", "text-1": "#e2e2e2", "text-2": "#ababab" }, "custom_cards": ["https://64.media.tumblr.com/5afa537025ecf339d036e3e4c40bb789/ebc602d9ff1556c2-e5/s500x750/96ff3e448a20a3860df586216424a38a9e6005d3.gif", "https://i.pinimg.com/originals/77/f5/58/77f5586fe7b43e5014ddf36ccb6ecca5.gif", "https://robbreport.com/wp-content/uploads/2022/11/f5005.jpg", "https://i.pinimg.com/originals/84/6f/c1/846fc1ef071081e340203d03ce0a659c.gif", "https://robbreport.com/wp-content/uploads/2020/04/1-18.jpg?w=1000"], "card_colors": ["#d00000", "#cb0000", "#c60000", "#c10000", "#bc0000"], "custom_font": { "family": "'Oswald'", "link": "Oswald:wght@400;700" } }, "preview": "https://robbreport.com/wp-content/uploads/2020/04/1-18.jpg?w=1000" },
{ "title": "Lana by G!llnm", "exports": { "disable_color_overlay": true, "gradient_cards": false, "dark_mode": true, "dark_preset": { "background-0": "#272727", "background-1": "#f570be", "background-2": "#feb4df", "borders": "#f570be", "links": "#f570be", "sidebar": "#f570be", "sidebar-text": "#ffffff", "text-0": "#fbe5f2", "text-1": "#ffc2e5", "text-2": "#ffd1ec" }, "custom_cards": ["https://i.pinimg.com/236x/d2/21/2f/d2212f198ab82da0646f879e13119c43.jpg", "https://i.pinimg.com/236x/72/58/ff/7258ff2ccae2c84e49e4a426c1ef48f1.jpg", "https://i.pinimg.com/736x/5d/8b/c6/5d8bc614d74968331aa140472cc0f263.jpg", "https://i.pinimg.com/736x/46/1b/2e/461b2e238350207a66453d56573c4a64.jpg", "https://i.pinimg.com/564x/d5/8e/11/d58e11500934d54481e805b32d46f049.jpg", "https://i.pinimg.com/736x/ab/8b/e3/ab8be3c609b511b7c5a6a290cc4bd7f6.jpg"], "card_colors": ["#f570be"], "custom_font": { "family": "'Jost'", "link": "Jost:wght@400;700" } }, "preview": "https://i.pinimg.com/236x/72/58/ff/7258ff2ccae2c84e49e4a426c1ef48f1.jpg" },
{ "title": "toroinoue by cheerios", "exports": { "disable_color_overlay": false, "gradient_cards": false, "dark_mode": true, "dark_preset": { "background-0": "#3c3c3c", "background-1": "#262626", "background-2": "#262626", "borders": "#dce9fc", "links": "#FEC5BB", "sidebar": "#dce9fc", "sidebar-text": "#161616", "text-0": "#dce9fc", "text-1": "#dce9fc", "text-2": "#ababab" }, "custom_cards": ["https://i.pinimg.com/564x/a7/7c/36/a77c363a2aa28a7f37a63b4f9e08a3a6.jpg", "https://i.pinimg.com/564x/27/2e/e9/272ee9c495377b9ad991661b58d1f83b.jpg", "https://i.pinimg.com/564x/85/0d/a2/850da2f2fe8c2cda43a67d9dd9a1112d.jpg", "https://i.pinimg.com/564x/55/38/2b/55382b4f53134077ec51de976c9b6138.jpg", "https://i.pinimg.com/564x/2f/1a/6a/2f1a6a55e983c89787b2c0aa574ba1f9.jpg", "https://i.pinimg.com/564x/c1/cd/ff/c1cdffa1a06c6f1f11c34d568b41909a.jpg", "https://i.pinimg.com/564x/d8/12/02/d81202e4d1fbe4849440f475bf139a5a.jpg", "https://i.pinimg.com/564x/92/ce/d5/92ced51467bf37f40cf1330fad756352.jpg", "https://i.pinimg.com/564x/d7/37/22/d73722fdc504b7152ad401613485e076.jpg", "https://i.pinimg.com/564x/05/0a/bf/050abf66c2fde3e7bb733bc018fcec8c.jpg"], "card_colors": ["#cddafd", "#fffae5", "#e2ece9", "#d6e2e9", "#fde2e4", "#f0efeb", "#fff1e6", "#610345", "#bee1e6", "#dfe7fd", "#fad2e1"], "custom_font": { "family": "'Kanit'", "link": "Kanit:wght@400;700" } }, "preview": "https://i.pinimg.com/564x/a7/7c/36/a77c363a2aa28a7f37a63b4f9e08a3a6.jpg" },
{ "title": "MercedesF1 by Ryan", "exports": { "disable_color_overlay": true, "gradient_cards": false, "dark_mode": true, "dark_preset": { "background-0": "#161616", "background-1": "#000000", "background-2": "#000000", "borders": "#ffffff", "links": "#64ebed", "sidebar": "#64ebed", "sidebar-text": "#000000", "text-0": "#ffffff", "text-1": "#ffffff", "text-2": "#ffffff" }, "custom_cards": ["https://speedcafe.us/wp-content/uploads/M409049.jpg_20241501_12x8.jpg", "https://encrypted-tbn0.gstatic.com/images?q=tbn:ANd9GcR0R1mS8Ls3axH-cdn4NMoFLo_KHaxVVV-s2w&usqp=CAU", "https://www.si.com/.image/ar_16:9%2Cc_fill%2Ccs_srgb%2Cfl_progressive%2Cg_faces:center%2Cq_auto:good%2Cw_768/MTk2NjI5MDY4NjkzNzEwODE1/m359635.jpg", "https://encrypted-tbn0.gstatic.com/images?q=tbn:ANd9GcS-RxbYRY45JyHlb-PlTvfCBXB20kuabVEDoQ&usqp=CAU", "https://encrypted-tbn0.gstatic.com/images?q=tbn:ANd9GcTDSTgAFEuLs8PrWhC5ZLl1nZewWA5dY7qrmA&usqp=CAU", "https://media.cnn.com/api/v1/images/stellar/prod/221113195421-george-russell-celebrate-brazil-gp-2.jpg?c=original"], "card_colors": ["#00ffff"], "custom_font": { "family": "'Karla'", "link": "Karla:wght@400;700" } }, "preview": "https://encrypted-tbn0.gstatic.com/images?q=tbn:ANd9GcR0R1mS8Ls3axH-cdn4NMoFLo_KHaxVVV-s2w&usqp=CAU" },
{ "title": "HTGAWM by Mechiel", "exports": { "disable_color_overlay": true, "gradient_cards": false, "dark_mode": true, "dark_preset": { "background-0": "#161616", "background-1": "#212121", "background-2": "#262626", "borders": "#ff3333", "links": "#ff3333", "sidebar": "#1e1e1e", "sidebar-text": "#f5f5f5", "text-0": "#ffffff", "text-1": "#ffffff", "text-2": "#ffffff" }, "custom_cards": ["https://i.pinimg.com/564x/77/70/ae/7770ae5b6a4c4ca591d8ef6b74944aef.jpg", "https://i.pinimg.com/564x/ec/4f/ef/ec4fefc85d7639316671418c02321044.jpg", "https://i.pinimg.com/564x/d7/27/ff/d727ff8eef52d4e5c52478657c8d48c7.jpg", "https://i.pinimg.com/564x/40/09/73/4009736649e9d5ff79ca0473af4c17ea.jpg", "https://i.pinimg.com/564x/09/80/40/0980404ccf0de49ed7d85891f0532cbf.jpg", "https://i.pinimg.com/564x/a4/b8/3f/a4b83f899ce693f1fd9d2b14048c5306.jpg", "https://i.pinimg.com/736x/84/cb/52/84cb525fcee2455711aa0c359897d946.jpg", "https://i.pinimg.com/564x/d1/bb/cc/d1bbccbb76f20912716c99dd4536e188.jpg", "https://i.pinimg.com/564x/aa/ad/e5/aaade5083aedc59ba681318d369338a3.jpg"], "card_colors": ["#ff3333"], "custom_font": { "family": "'Cinzel'", "link": "Cinzel:wght@400;700" } }, "preview": "https://i.pinimg.com/564x/77/70/ae/7770ae5b6a4c4ca591d8ef6b74944aef.jpg" },
{ "title": "F1 by Max", "exports": { "disable_color_overlay": true, "gradient_cards": false, "dark_mode": true, "dark_preset": { "background-0": "#161616", "background-1": "#1e1e1e", "background-2": "#262626", "borders": "#3c3c3c", "links": "#19a4a7", "sidebar": "#19a4a7", "sidebar-text": "#000000", "text-0": "#f5f5f5", "text-1": "#e2e2e2", "text-2": "#ababab" }, "custom_cards": ["https://i.pinimg.com/564x/71/cd/11/71cd1147f3db16a4d8e9e1a04cb6ee83.jpg", "https://i.pinimg.com/564x/53/cb/1a/53cb1a849f93a52e5f9e622bfaf39e3b.jpg", "https://i.pinimg.com/564x/ef/f6/37/eff6376ec893df6b023b67eb43b12aa6.jpg", "https://i.pinimg.com/564x/6c/32/0d/6c320d77a25507c9335540ee5e590375.jpg"], "card_colors": ["#19a4a7"], "custom_font": { "family": "'Rubik'", "link": "Rubik:wght@400;700" } }, "preview": "https://i.pinimg.com/564x/53/cb/1a/53cb1a849f93a52e5f9e622bfaf39e3b.jpg" },
{ "title": "OSU by Anonymous", "exports": { "disable_color_overlay": true, "gradient_cards": false, "dark_mode": true, "dark_preset": { "background-0": "#232323", "background-1": "#353535", "background-2": "#404040", "borders": "#454545", "links": "#FCB0BF", "sidebar": "linear-gradient(#666666, #BB0000)", "sidebar-text": "#f5f5f5", "text-0": "#f5f5f5", "text-1": "#e2e2e2", "text-2": "#ababab" }, "custom_cards": ["https://upload.wikimedia.org/wikipedia/commons/thumb/c/c1/Ohio_State_Buckeyes_logo.svg/350px-Ohio_State_Buckeyes_logo.svg.png", "https://encrypted-tbn0.gstatic.com/images?q=tbn:ANd9GcQfyXvEJvF2uqkWj4BlCu6twOgF9Fyf4ESZ0iBEcfwVog&s", "https://upload.wikimedia.org/wikipedia/commons/thumb/5/59/Ohio_State_University_Logo.svg/2048px-Ohio_State_University_Logo.svg.png", "https://content.sportslogos.net/logos/33/791/full/ohio_state_buckeyes_logo_alt_on_dark_1973_sportslogosnet-8881.png", "https://upload.wikimedia.org/wikipedia/en/thumb/e/e1/Ohio_State_University_seal.svg/300px-Ohio_State_University_seal.svg.png"], "card_colors": ["#ffffff", "#000000", "#ffffff", "#000000", "#ffffff", "#000000"], "custom_font": { "family": "", "link": "" } }, "preview": "https://upload.wikimedia.org/wikipedia/commons/thumb/c/c1/Ohio_State_Buckeyes_logo.svg/350px-Ohio_State_Buckeyes_logo.svg.png" },
{ "title": "F1Teams by EthanF1", "exports": { "disable_color_overlay": true, "gradient_cards": false, "dark_mode": true, "dark_preset": { "background-0": "#000000", "background-1": "#000000", "background-2": "#000000", "borders": "#000000", "links": "#a30000", "sidebar": "linear-gradient(#000000c7, #000000c7), center url(\"https://i.pinimg.com/564x/4f/5f/5e/4f5f5e140f1911e54e3cd761316ba12f.jpg\")", "sidebar-text": "#ffffff", "text-0": "#f5f5f5", "text-1": "#e2e2e2", "text-2": "#ababab" }, "custom_cards": ["https://media.licdn.com/dms/image/C4E22AQGOYToW8jpiXg/feedshare-shrink_800/0/1672766140689?e=2147483647&v=beta&t=yYd65eO2aFw034AenJFrUWO_QXoBCwvE4EA2rO-8jwk", "https://preview.redd.it/i-made-a-team-mclaren-poster-for-the-2023-japanese-gp-v0-v3f68vnkfxqb1.jpg?width=640&crop=smart&auto=webp&s=350cbe264dc5090d9b6893d2bfc19433eb188670", "https://i.ebayimg.com/images/g/7QsAAOSwdmZgliA-/s-l1200.webp", "https://m.media-amazon.com/images/I/71DvgAmPErL._AC_UF1000,1000_QL80_.jpg", "https://media.formula1.com/content/dam/fom-website/sutton/2022/Brazil/Friday/1440803811.jpg.img.1536.high.jpg", "https://f1i.com/wp-content/uploads/2019/05/Leclerc.jpg"], "card_colors": ["#737373"], "custom_font": { "family": "'Oswald'", "link": "Oswald:wght@400;700" } }, "preview": "https://preview.redd.it/i-made-a-team-mclaren-poster-for-the-2023-japanese-gp-v0-v3f68vnkfxqb1.jpg?width=640&crop=smart&auto=webp&s=350cbe264dc5090d9b6893d2bfc19433eb188670" },
{ "title": "Nissan by Liam", "exports": { "disable_color_overlay": true, "gradient_cards": false, "dark_mode": true, "dark_preset": { "background-0": "#161616", "background-1": "#000000", "background-2": "#000000", "borders": "#ffffff", "links": "#FFFFFF", "sidebar": "linear-gradient(#444444, #666666)", "sidebar-text": "#FFFFFF", "text-0": "#ffffff", "text-1": "#ffffff", "text-2": "#ffffff" }, "custom_cards": ["https://encrypted-tbn0.gstatic.com/images?q=tbn:ANd9GcSv4oFXZSsltT7xSg8aZU5R74DymUJC4nkxCKBLzaS9eA&s", "https://encrypted-tbn0.gstatic.com/images?q=tbn:ANd9GcQIxIakUUlyRafvQKZOvtIVuG7Qe3qmoS0NGy7jIHpijA&s", "https://external-preview.redd.it/ue-XAfuEpbd7NrTtj-Zob-8eXwzujyznSDcD6JMJAPs.jpg?auto=webp&s=5e5d16c91996d363fd99952644aa6a10d36063cf", "https://i.pinimg.com/originals/e3/68/60/e36860e156dd107ef34b14f87ca7291c.jpg", "https://i.redd.it/t6joqp50rre31.jpg", "https://pbs.twimg.com/media/Dwvvc2vX0AEwb7k.jpg:large", "https://i.pinimg.com/originals/82/1b/c3/821bc384d1cbba06159f2b4129fee4da.jpg", "https://i.pinimg.com/originals/65/44/de/6544deb27eebee16358f635b5fd84e85.jpg"], "card_colors": ["#FFFFFF"], "custom_font": { "family": "'Varela'", "link": "Varela:wght@400;700" } }, "preview": "https://encrypted-tbn0.gstatic.com/images?q=tbn:ANd9GcQIxIakUUlyRafvQKZOvtIVuG7Qe3qmoS0NGy7jIHpijA&s" },
{ "title": "BMW by Hamza", "exports": { "disable_color_overlay": true, "gradient_cards": false, "dark_mode": true, "dark_preset": { "background-0": "#403f3f", "background-1": "#000000", "background-2": "#020061", "borders": "#020061", "links": "#ffffff", "sidebar": "linear-gradient(#000000, #000875)", "sidebar-text": "#ffffff", "text-0": "#4a47ff", "text-1": "#ffffff", "text-2": "#ffffff" }, "custom_cards": ["https://i.ytimg.com/vi/w5nvqBdM-go/hq720.jpg?sqp=-oaymwEhCK4FEIIDSFryq4qpAxMIARUAAAAAGAElAADIQj0AgKJD&rs=AOn4CLCFMhh2O5WRww1rN1vQSMepz3eTPA", "https://www.keepyourcarsafe.co.uk/cdn/shop/products/DSC_0710_d0c3b229-b2b2-4888-8009-19beb0af2133_1946x.jpg?v=1609605860", "https://image-cdn.hypb.st/https%3A%2F%2Fhypebeast.com%2Fimage%2F2022%2F01%2Fmanhart-mh8-800-limited-01-10-bmw-m8-competition-v8-tuned-rare-german-super-coupe-3.jpg?cbr=1&q=90", "https://www.vegasautogallery.com/imagetag/512/29/l/Used-2020-BMW-M5-Competition-1614113063.jpg", "https://cloudfront-us-east-2.images.arcpublishing.com/reuters/U6DU4EGVOZNXPHXTMIPF7B5C64.jpg"], "card_colors": ["#171717"], "custom_font": { "family": "'Montserrat'", "link": "Montserrat:wght@400;700" } }, "preview": "https://i.ytimg.com/vi/w5nvqBdM-go/hq720.jpg?sqp=-oaymwEhCK4FEIIDSFryq4qpAxMIARUAAAAAGAElAADIQj0AgKJD&rs=AOn4CLCFMhh2O5WRww1rN1vQSMepz3eTPA" },
{ "title": "RainyDay by CMHEIK", "exports": { "disable_color_overlay": true, "gradient_cards": false, "dark_mode": true, "dark_preset": { "background-0": "#161616", "background-1": "#1e1e1e", "background-2": "#262626", "borders": "#3c3c3c", "links": "#A3B18A", "sidebar": "#496E4C", "sidebar-text": "#DAD7CD", "text-0": "#DAD7CD", "text-1": "#DAD7CD", "text-2": "#DAD7CD" }, "custom_cards": ["https://cdn.kibrispdr.org/data/1755/anime-rain-gif-50.gif", "https://i.pinimg.com/originals/65/8d/8e/658d8eb90b08dcf7c18c7a7cfba2ea50.gif", "https://i.pinimg.com/originals/dd/54/b7/dd54b7ddc13906fbb8b5e97ab6c3f119.gif", "https://i.imgur.com/fpTddbw.gif", "https://i.redd.it/ux93fxldhoxa1.gif", "https://64.media.tumblr.com/4d8dd5743f454682d3d03303dba81eb8/tumblr_p5lt9dnoOO1uhx88zo1_500.gif", "https://img.wattpad.com/145da2e6f66d74c429ebe8baff51887bf408c2d5/68747470733a2f2f73332e616d617a6f6e6177732e636f6d2f776174747061642d6d656469612d736572766963652f53746f7279496d6167652f6358354a334c6234355a343150513d3d2d313135333131393938302e313665346432313634333930363166353830343432343937343930382e676966"], "card_colors": ["#344e41", "#375441", "#588157", "#496e4c", "#3a5a40", "#a3b18a", "#7e9971"], "custom_font": { "family": "", "link": "" } }, "preview": "https://img.wattpad.com/145da2e6f66d74c429ebe8baff51887bf408c2d5/68747470733a2f2f73332e616d617a6f6e6177732e636f6d2f776174747061642d6d656469612d736572766963652f53746f7279496d6167652f6358354a334c6234355a343150513d3d2d313135333131393938302e313665346432313634333930363166353830343432343937343930382e676966" },
{ "title": "TTPD by Brody", "exports": { "disable_color_overlay": false, "gradient_cards": false, "dark_mode": true, "dark_preset": { "background-0": "#272727", "background-1": "#353535", "background-2": "#404040", "borders": "#454545", "links": "#56Caf0", "sidebar": "#353535", "sidebar-text": "#f5f5f5", "text-0": "#f5f5f5", "text-1": "#e2e2e2", "text-2": "#ababab" }, "custom_cards": ["https://assets.teenvogue.com/photos/65e5e30bb3acbf1a5964e0cf/16:9/w_1280,c_limit/431129483_288082554301322_5338342243495667848_n%20(1).jpg", "https://preview.redd.it/the-tortured-poets-department-the-albatross-edition-v0-bgnc9ahvackc1.jpg?width=640&crop=smart&auto=webp&s=1bfd5edbd540e1c8b52aa59ee0209b14d3482831", "https://www.mdtech.news/u/fotografias/m/2024/2/9/f768x400-36910_80813_20.png", "https://i0.wp.com/www.marieclaire.com.au/wp-content/uploads/sites/5/2024/02/taylor-swift-the-tortured-poets-department-track-listing-explained.jpg?fit=1920%2C1080&ssl=1", "https://vipertimes.com/wp-content/uploads/2024/02/CWIUdn3xdTyXWyirAKD1FOJeBwiNfVp56HYvXM0B.png", "https://www.comingsoon.net/wp-content/uploads/sites/3/2024/02/taylor-swift-Tortured-Poets-Department-release-party-dates-when-how-to-get-tickets.jpg", "https://variety.com/wp-content/uploads/2024/02/Screenshot-2024-02-16-at-3.41.29-AM.png?w=1017", "https://lorena.r7.com/public/assets/img/postagens/post_58061.jpg", "https://wegotthiscovered.com/wp-content/uploads/2024/02/Taylor-Swift-Tortured-Poets-Department-2.jpg"], "card_colors": ["#767676"], "custom_font": { "family": "'Cinzel'", "link": "Cinzel:wght@400;700" } }, "preview": "https://vipertimes.com/wp-content/uploads/2024/02/CWIUdn3xdTyXWyirAKD1FOJeBwiNfVp56HYvXM0B.png" },
{ "title": "Crocodile by Samira", "exports": { "disable_color_overlay": true, "gradient_cards": false, "dark_mode": false, "custom_cards": ["https://i.pinimg.com/originals/6f/1e/62/6f1e6295d79f2e18fff6fc0709d884a5.jpg", "https://i.pinimg.com/originals/3d/2e/ac/3d2eacffd5d9204bbf4801ad55107ce7.jpg", "https://i.pinimg.com/originals/76/96/a1/7696a129f91b51b93939be66e4342c44.jpg", "https://i.pinimg.com/originals/01/7c/49/017c4904ab5ab0390bed9db63932dfd9.jpg", "https://i.pinimg.com/originals/33/8d/79/338d79861a7274cb60b456d3448ad98f.jpg"], "card_colors": ["#286914", "#347723", "#408532", "#4d9341", "#59a050", "#65ae5f", "#71bc6e"], "custom_font": { "family": "'Happy Monkey'", "link": "Happy+Monkey:wght@400;700" } }, "preview": "https://i.pinimg.com/originals/76/96/a1/7696a129f91b51b93939be66e4342c44.jpg" },
{ "title": "Hutcherson by Rachel", "exports": { "disable_color_overlay": false, "gradient_cards": false, "dark_mode": false, "custom_cards": ["https://media1.tenor.com/m/b7PcCEZRv08AAAAC/josh-hutcherson.gif"], "card_colors": ["#e1d5d7", "#f06291", "#65499d", "#009688", "#0b9be3", "#ff2717", "#d97900"], "custom_font": { "family": "'Oswald'", "link": "Oswald:wght@400;700" } }, "preview": "https://media1.tenor.com/m/b7PcCEZRv08AAAAC/josh-hutcherson.gif" },
{ "title": "Bugs by Avery", "exports": { "disable_color_overlay": true, "gradient_cards": false, "dark_mode": false, "custom_cards": ["https://i.pinimg.com/564x/e4/0a/ef/e40aefac57a2318fdd89655c46c72edb.jpg", "https://i.pinimg.com/564x/f6/f2/eb/f6f2eb8fae2a1f1dd5fb0da549d7a9b4.jpg", "https://i.pinimg.com/564x/23/69/96/236996b8212a2141cb3d6f717fbce870.jpg", "https://i.pinimg.com/564x/ea/39/60/ea396036cfa456bcc86cb357adf0c899.jpg"], "card_colors": ["#f2f230", "#c2f261", "#91f291", "#61f2c2"], "custom_font": { "family": "'Corben'", "link": "Corben:wght@400;700" } }, "preview": "https://i.pinimg.com/564x/f6/f2/eb/f6f2eb8fae2a1f1dd5fb0da549d7a9b4.jpg" },
{ "title": "Affection by Maggie", "exports": { "disable_color_overlay": false, "gradient_cards": true, "dark_mode": false, "custom_cards": ["https://inasianspaces.files.wordpress.com/2024/01/itsuomi-charming-yuki-while-holding-tea-a-sign-of-affection-episode-3.png?w=1200", "https://i.imgur.com/teoUw5s.png", "https://i0.wp.com/anitrendz.net/news/wp-content/uploads/2023/10/asignofaffection_pv1screenshot.png", "https://i.imgur.com/teoUw5s.png", "https://rabujoi.files.wordpress.com/2024/01/soa41.jpg", "https://i.imgur.com/qcmICyR.png", "https://a.storyblok.com/f/178900/750x422/b8cde0dca4/a-sign-of-affection.jpg/m/filters:quality(95)format(webp)"], "card_colors": ["#cdb4db", "#ffc8dd", "#ffafcc", "#bde0fe", "#a2d2ff", "#cdb4db"], "custom_font": { "link": "Rakkas:wght@400;700", "family": "'Rakkas'" } }, "preview": "https://rabujoi.files.wordpress.com/2024/01/soa41.jpg" },
*/
]