Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
43 commits
Select commit Hold shift + click to select a range
8ff2bf8
refactor: example usage of solid/tsx (@fehmer)
fehmer Jan 8, 2026
b36b73f
refactor, tests
fehmer Jan 8, 2026
87f70ac
fix lint issue
fehmer Jan 8, 2026
8169bfd
only update live speed if enabled
fehmer Jan 8, 2026
396b95e
move stuff around
fehmer Jan 8, 2026
0e4bcfa
on a page
fehmer Jan 8, 2026
fa0611c
convert live stats
fehmer Jan 8, 2026
5627336
remove account experiment
fehmer Jan 8, 2026
205a515
dont export state setters
Miodec Jan 8, 2026
75a36c9
use signals for focus and isactive state
Miodec Jan 8, 2026
4007f43
pre-commit lint
fehmer Jan 8, 2026
bca19b4
obsolete
fehmer Jan 8, 2026
80d8c22
animation wip
Miodec Jan 8, 2026
e9fcf1f
need to ignore lint error
Miodec Jan 8, 2026
f6fe948
util
Miodec Jan 8, 2026
1bae0e7
final
Miodec Jan 8, 2026
a297539
no rename
Miodec Jan 8, 2026
12bb3dd
no memo
Miodec Jan 8, 2026
bf50fe7
export hook
Miodec Jan 8, 2026
3f20d89
rename
Miodec Jan 8, 2026
97b54b6
improve hook
Miodec Jan 8, 2026
71f93d7
type
Miodec Jan 8, 2026
2056487
one object
Miodec Jan 8, 2026
082adde
sweep
Miodec Jan 8, 2026
7b86390
ref with utils, move isfocused up
Miodec Jan 8, 2026
883e436
refactor
Miodec Jan 8, 2026
2d0c8df
renames
Miodec Jan 8, 2026
b5fa8ad
unused import
Miodec Jan 8, 2026
9013fdb
reduced motion
fehmer Jan 8, 2026
e29ff7a
optional visibility options
fehmer Jan 8, 2026
ec0e15e
move and rename
Miodec Jan 8, 2026
a86c2f1
refactor
Miodec Jan 8, 2026
ff6c6f3
rename
Miodec Jan 8, 2026
457a158
fix
fehmer Jan 8, 2026
e34eb6d
fix
Miodec Jan 8, 2026
af35057
dont export
Miodec Jan 8, 2026
645eaeb
support hide
Miodec Jan 8, 2026
97c50aa
update value
Miodec Jan 8, 2026
610be26
move timer state outside
Miodec Jan 8, 2026
435794e
remove LiveStatsMini
fehmer Jan 8, 2026
091dcf7
fix existing tests, add component test
fehmer Jan 9, 2026
b3adfcc
cleanup
fehmer Jan 9, 2026
048c4a1
implement color, opacity change config to a single signal
Miodec Jan 9, 2026
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
104 changes: 104 additions & 0 deletions frontend/__tests__/components/test/LiveStats.jsdom-spec.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,104 @@
import { describe, vi, it, expect, beforeEach, Mock } from "vitest";
import { createSignal } from "solid-js";
import { render } from "@solidjs/testing-library";
import { LiveStats } from "../../../src/ts/components/test/LiveStats";

import * as ConfigSignals from "../../../src/ts/signals/config";
import * as TestSignals from "../../../src/ts/signals/test";

import { isFocused } from "../../../src/ts/test/focus";

describe("LiveStats", () => {
const [wpm] = createSignal("120");
const [acc] = createSignal("98%");
const [burst] = createSignal("140");

const liveSpeedStyleMock = vi.spyOn(ConfigSignals, "getLiveSpeedStyle");
const liveAccStyleMock = vi.spyOn(ConfigSignals, "getLiveAccStyle");
const liveBurstStyleMock = vi.spyOn(ConfigSignals, "getLiveBurstStyle");
const statsVisibleMock = vi.spyOn(TestSignals, "statsVisible");

beforeEach(() => {
[
isFocused as Mock,
liveSpeedStyleMock,
liveAccStyleMock,
liveBurstStyleMock,
statsVisibleMock,
].forEach((it) => it.mockClear());

(isFocused as Mock).mockReturnValue(true);
liveSpeedStyleMock.mockReturnValue("text");
liveBurstStyleMock.mockReturnValue("text");
liveAccStyleMock.mockReturnValue("text");
statsVisibleMock.mockReturnValue({ visible: true, animate: false });
});

function renderElement(mode: "mini" | "text"): {
speed: HTMLElement;
acc: HTMLElement;
burst: HTMLElement;
} {
const { container } = render(() => (
<LiveStats mode={mode} wpm={wpm} acc={acc} burst={burst} />
));

return {
// oxlint-disable-next-line no-non-null-assertion
speed: container.querySelector(".speed")!,
// oxlint-disable-next-line no-non-null-assertion
acc: container.querySelector(".acc")!,
// oxlint-disable-next-line no-non-null-assertion
burst: container.querySelector(".burst")!,
};
}

it("does render if mode matches", () => {
//GIVEN

//WHEN
const { speed, acc, burst } = renderElement("text");

//THEN
expect(speed).toHaveAttribute("data-visible", "true");
expect(speed).toHaveTextContent("120");
expect(acc).toHaveAttribute("data-visible", "true");
expect(acc).toHaveTextContent("98%");
expect(burst).toHaveAttribute("data-visible", "true");
expect(burst).toHaveTextContent("140");
});
it("does not render if mode does not match", () => {
//WHEN
const { speed, acc, burst } = renderElement("mini");

//THEN
expect(speed).toHaveAttribute("data-visible", "false");
expect(acc).toHaveAttribute("data-visible", "false");
expect(burst).toHaveAttribute("data-visible", "false");
});

it("does not render if not focussed", () => {
//GIVEN
(isFocused as Mock).mockReturnValue(false);

//WHEN
const { speed, acc, burst } = renderElement("text");

//WHEN
expect(speed).toHaveAttribute("data-visible", "false");
expect(acc).toHaveAttribute("data-visible", "false");
expect(burst).toHaveAttribute("data-visible", "false");
});
it("does not render if statsVisible=false", () => {
//GIVEN
statsVisibleMock.mockReturnValue({ visible: false });

//WHEN
const { speed, acc, burst } = renderElement("text");

//WHEN
expect(speed).toHaveAttribute("data-visible", "false");
expect(acc).toHaveAttribute("data-visible", "false");
expect(burst).toHaveAttribute("data-visible", "false");
});
});
2 changes: 1 addition & 1 deletion frontend/__tests__/root/config.spec.ts
Original file line number Diff line number Diff line change
Expand Up @@ -53,7 +53,7 @@ describe("Config", () => {
mocks.forEach((it) => it.mockClear());

vi.mock("../../src/ts/test/test-state", () => ({
isActive: true,
isActive: () => true,
}));

isConfigValueValidMock.mockReturnValue(true);
Expand Down
15 changes: 15 additions & 0 deletions frontend/__tests__/setup-jsdom.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,21 @@
import $ from "jquery";
import { vi } from "vitest";
import "@testing-library/jest-dom";
import { getDefaultConfig } from "../src/ts/constants/default-config";

//@ts-expect-error add to global
global["$"] = $;
//@ts-expect-error add to global
global["jQuery"] = $;

vi.mock("../src/ts/config", () => {
return {
default: getDefaultConfig(),
};
});

vi.mock("../src/ts/test/focus", () => {
return {
isFocused: vi.fn(),
};
});
11 changes: 9 additions & 2 deletions frontend/__tests__/tsconfig.json
Original file line number Diff line number Diff line change
Expand Up @@ -3,8 +3,15 @@
"compilerOptions": {
"moduleResolution": "Bundler",
"module": "ESNext",
"noEmit": true
"noEmit": true,
"jsx": "preserve",
"jsxImportSource": "solid-js"
},
"files": ["vitest.d.ts"],
"include": ["./**/*.spec.ts", "./**/*.jsdom-spec.ts", "./setup-tests.ts"]
"include": [
"./**/*.spec.ts",
"./**/*.jsdom-spec.ts",
"./**/*.jsdom-spec.tsx",
"./setup-tests.ts"
]
}
4 changes: 2 additions & 2 deletions frontend/__tests__/utils/dom.jsdom-spec.ts
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,7 @@ describe("dom", () => {
}

beforeEach(() => {
handler.mockReset();
handler.mockClear();

document.body.innerHTML = "";
const root = document.createElement("div");
Expand Down Expand Up @@ -151,7 +151,7 @@ describe("dom", () => {
);

//WHEN click on mid1 handler is only called one time
handler.mockReset();
handler.mockClear();
clickTarget = screen.getByTestId("mid1");
await userEvent.click(clickTarget);

Expand Down
3 changes: 3 additions & 0 deletions frontend/__tests__/vitest.d.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,9 @@
import type { Assertion, AsymmetricMatchersContaining } from "vitest";
import { TestActivityDay } from "../src/ts/elements/test-activity-calendar";

/// <reference types="vitest" />
import "@testing-library/jest-dom";

interface ActivityDayMatchers<R = TestActivityDay> {
toBeDate: (date: string) => ActivityDayMatchers<R>;
toHaveTests: (tests: number) => ActivityDayMatchers<R>;
Expand Down
4 changes: 4 additions & 0 deletions frontend/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -61,7 +61,9 @@
"@fortawesome/fontawesome-free": "5.15.4",
"@monkeytype/oxlint-config": "workspace:*",
"@monkeytype/typescript-config": "workspace:*",
"@solidjs/testing-library": "0.8.10",
"@testing-library/dom": "10.4.1",
"@testing-library/jest-dom": "6.9.1",
"@testing-library/user-event": "14.6.1",
"@types/canvas-confetti": "1.4.3",
"@types/chartjs-plugin-trendline": "1.0.1",
Expand All @@ -87,6 +89,7 @@
"oxlint-tsgolint": "0.10.1",
"postcss": "8.4.31",
"sass": "1.70.0",
"solid-js": "1.9.10",
"subset-font": "2.3.0",
"tsx": "4.16.2",
"typescript": "5.9.3",
Expand All @@ -98,6 +101,7 @@
"vite-plugin-inspect": "11.3.3",
"vite-plugin-minify": "2.1.0",
"vite-plugin-pwa": "1.1.0",
"vite-plugin-solid": "2.11.10",
"vitest": "4.0.15"
},
"lint-staged": {
Expand Down
21 changes: 3 additions & 18 deletions frontend/src/html/pages/test.html
Original file line number Diff line number Diff line change
Expand Up @@ -124,17 +124,8 @@
<div id="memoryTimer">Time left to memorise all words: 0s</div>
<div id="layoutfluidTimer">Time left to memorise all words: 0s</div>
<div id="testModesNotice"></div>
<div id="liveStatsTextTop" class="timerMain">
<div class="wrapper">
<div class="timerProgress hidden">1:00</div>
</div>
</div>
<div id="liveStatsMini" class="full-width timerMain">
<div class="time hidden">1:00</div>
<div class="speed hidden">60</div>
<div class="acc hidden">100%</div>
<div class="burst hidden">1</div>
</div>
<div id="liveStatsTextTop"></div>
<div id="liveStatsMini" class="full-width"></div>
<div id="wordsWrapper" class="content-grid full-width" translate="no">
<textarea
id="wordsInput"
Expand Down Expand Up @@ -170,13 +161,7 @@
>
<i class="fas fa-fw fa-redo-alt"></i>
</button>
<div id="liveStatsTextBottom" class="timerMain">
<div class="wrapper">
<div class="liveSpeed hidden">123</div>
<div class="liveAcc hidden">100%%</div>
<div class="liveBurst hidden">1</div>
</div>
</div>
<div id="liveStatsTextBottom" class="timerMain"></div>
<div id="monkey" class="hidden">
<div class="up"></div>
<div class="left hidden"></div>
Expand Down
95 changes: 31 additions & 64 deletions frontend/src/styles/test.scss
Original file line number Diff line number Diff line change
Expand Up @@ -124,7 +124,6 @@
display: grid;
font-size: 10rem;

opacity: 0;
width: 0;
height: 0;
justify-self: center;
Expand Down Expand Up @@ -163,26 +162,26 @@
}
}

#liveStatsTextBottom.timerMain,
#liveStatsTextTop.timerMain {
#liveStatsTextBottom .colorMain,
#liveStatsTextTop .colorMain {
color: var(--main-color);
}

#barTimerProgress.timerMain .bar {
background: var(--main-color);
}

#liveStatsTextBottom.timerSub,
#liveStatsTextTop.timerSub {
#liveStatsTextBottom .colorSub,
#liveStatsTextTop .colorSub {
color: var(--sub-color);
}

#barTimerProgress.timerSub .bar {
background: var(--sub-color);
}

#liveStatsTextBottom.timerText,
#liveStatsTextTop.timerText {
#liveStatsTextBottom .colorText,
#liveStatsTextTop .colorText {
color: var(--text-color);
}

Expand Down Expand Up @@ -1474,68 +1473,36 @@
}
}
#liveStatsMini {
width: 0;
justify-content: start;
height: 0;
margin-left: 0.25em;
display: flex;
margin-top: -1.25em;
color: black;

div {
font-size: 1em;
line-height: 1em;
}

.time,
.speed,
.acc {
margin-right: 0.5em;
}
.wrapper {
width: 0;
justify-content: start;
height: 0;
display: flex;
margin-top: -1.25em;
color: black;

.time,
.speed,
.acc,
.burst {
opacity: 0;
}
div {
font-size: 1em;
line-height: 1em;
}

&.timerMain {
color: var(--main-color);
}
.time,
.speed,
.acc {
margin-right: 0.5em;
}

&.timerSub {
color: var(--sub-color);
}
&.colorMain {
color: var(--main-color);
}

&.timerText {
color: var(--text-color);
}
&.colorSub {
color: var(--sub-color);
}

&.size125 {
margin-top: -1.75rem;
font-size: 1.25rem;
line-height: 1.25rem;
}
&.size15 {
margin-top: -2rem;
font-size: 1.5rem;
line-height: 1.5rem;
}
&.size2 {
margin-top: -2.5rem;
font-size: 2rem;
line-height: 2rem;
}
&.size3 {
margin-top: -3.5rem;
font-size: 3rem;
line-height: 3rem;
}
&.size4 {
margin-top: -4.5rem;
font-size: 4rem;
line-height: 4rem;
&.colorText {
color: var(--text-color);
}
}
}
}
Expand Down
Loading
Loading