`;
}
}
@@ -4570,13 +4569,385 @@ $(document).on("click", "#testModesNotice .text-button", (event) => {
}
});
+let dontInsertSpace = false;
+
+//handle keyboard events
+$(document).keydown((event) => {
+ if (!resultVisible) {
+ let now = performance.now();
+ let diff = Math.abs(keypressStats.spacing.current - now);
+ if (keypressStats.spacing.current !== -1) {
+ keypressStats.spacing.array.push(diff);
+ }
+ keypressStats.spacing.current = now;
+ }
+
+ //tab
+ if (
+ (event.key == "Tab" && !config.swapEscAndTab) ||
+ (event.key == "Escape" && config.swapEscAndTab)
+ ) {
+ if (
+ !event.ctrlKey &&
+ config.quickTab &&
+ !$(".pageLogin").hasClass("active") &&
+ !resultCalculating &&
+ $("#commandLineWrapper").hasClass("hidden") &&
+ $("#simplePopupWrapper").hasClass("hidden")
+ ) {
+ event.preventDefault();
+ if ($(".pageTest").hasClass("active")) {
+ if (
+ (config.mode === "words" && config.words < 1000) ||
+ (config.mode === "time" && config.time < 3600) ||
+ config.mode === "quote" ||
+ (config.mode === "custom" &&
+ customTextIsRandom &&
+ customTextWordCount < 1000) ||
+ (config.mode === "custom" &&
+ !customTextIsRandom &&
+ customText.length < 1000)
+ ) {
+ if (testActive) {
+ let testNow = Date.now();
+ let testSeconds = roundTo2((testNow - testStart) / 1000);
+ incompleteTestSeconds += testSeconds;
+ restartCount++;
+ }
+ restartTest();
+ } else {
+ showNotification("Quick restart disabled for long tests", 2000);
+ }
+ } else {
+ changePage("test");
+ }
+ }
+ }
+
+ //only for the typing test
+ if ($("#wordsInput").is(":focus")) {
+ const isBackspace =
+ event.key === "Backspace" ||
+ (config.capsLockBackspace && event.key === "CapsLock");
+ if (isBackspace) {
+ event.preventDefault();
+ if (!testActive) return;
+ if (
+ currentInput == "" &&
+ inputHistory.length > 0 &&
+ currentWordElementIndex > 0
+ ) {
+ if (
+ (inputHistory[currentWordIndex - 1] ==
+ wordsList[currentWordIndex - 1] &&
+ !config.freedomMode) ||
+ $($(".word")[currentWordIndex - 1]).hasClass("hidden")
+ ) {
+ return;
+ } else {
+ if (config.confidenceMode === "on" || config.confidenceMode === "max")
+ return;
+ if (event["ctrlKey"] || event["altKey"]) {
+ currentInput = "";
+ inputHistory.pop();
+ correctedHistory.pop();
+ } else {
+ currentInput = inputHistory.pop();
+ currentCorrected = correctedHistory.pop();
+ }
+ currentWordIndex--;
+ currentWordElementIndex--;
+ updateActiveElement();
+ compareInput(!config.blindMode);
+ }
+ } else {
+ if (config.confidenceMode === "max") return;
+ if (event["ctrlKey"] || event["altKey"]) {
+ currentInput = "";
+ } else {
+ currentInput = currentInput.substring(0, currentInput.length - 1);
+ }
+ compareInput(!config.blindMode);
+ }
+ playClickSound();
+ if (config.keymapMode === "react") {
+ flashPressedKeymapKey(event.code, true);
+ } else if (config.keymapMode === "next") {
+ updateHighlightedKeymapKey();
+ }
+ updateCaretPosition();
+ }
+ //space
+ if (event.key === " ") {
+ if (!testActive) return;
+ if (currentInput === "") return;
+ event.preventDefault();
+ let currentWord = wordsList[currentWordIndex];
+ // if (config.mode == "time") {
+ if (!config.showAllLines || config.mode == "time") {
+ // let currentTop = Math.floor($($("#words .word")[currentWordIndex]).position().top);
+ // let nextTop = Math.floor($($("#words .word")[currentWordIndex + 1]).position().top);
+ if (config.stopOnError != "off") {
+ if (currentWord !== currentInput) return;
+ }
+
+ let currentTop = Math.floor(
+ document.querySelectorAll("#words .word")[currentWordElementIndex]
+ .offsetTop
+ );
+ let nextTop;
+ try {
+ nextTop = Math.floor(
+ document.querySelectorAll("#words .word")[
+ currentWordElementIndex + 1
+ ].offsetTop
+ );
+ } catch (e) {
+ nextTop = 0;
+ }
+
+ if ((nextTop > currentTop || activeWordJumped) && !lineTransition) {
+ //last word of the line
+ if (currentTestLine > 0) {
+ let hideBound = currentTop;
+ if (activeWordJumped) {
+ hideBound = activeWordTopBeforeJump;
+ }
+ activeWordJumped = false;
+
+ let toHide = [];
+ let wordElements = $("#words .word");
+ for (let i = 0; i < currentWordElementIndex + 1; i++) {
+ if ($(wordElements[i]).hasClass("hidden")) continue;
+ // let forWordTop = Math.floor($(wordElements[i]).position().top);
+ let forWordTop = Math.floor(wordElements[i].offsetTop);
+ if (forWordTop < hideBound - 10) {
+ // $($("#words .word")[i]).addClass("hidden");
+ toHide.push($($("#words .word")[i]));
+ }
+ }
+ const wordHeight = $(document.querySelector(".word")).outerHeight(
+ true
+ );
+ if (config.smoothLineScroll && toHide.length > 0) {
+ lineTransition = true;
+ $("#words").prepend(
+ `
`
+ );
+ $("#words .smoothScroller").animate(
+ {
+ height: 0,
+ },
+ 125,
+ () => {
+ $("#words .smoothScroller").remove();
+ }
+ );
+ $("#paceCaret").animate(
+ {
+ top:
+ document.querySelector("#paceCaret").offsetTop - wordHeight,
+ },
+ 125
+ );
+ $("#words").animate(
+ {
+ marginTop: `-${wordHeight}px`,
+ },
+ 125,
+ () => {
+ activeWordTop = document.querySelector("#words .active")
+ .offsetTop;
+
+ currentWordElementIndex -= toHide.length;
+ lineTransition = false;
+ toHide.forEach((el) => el.remove());
+ $("#words").css("marginTop", "0");
+ }
+ );
+ } else {
+ toHide.forEach((el) => el.remove());
+ currentWordElementIndex -= toHide.length;
+ $("#paceCaret").css({
+ top:
+ document.querySelector("#paceCaret").offsetTop - wordHeight,
+ });
+ }
+ // if (config.smoothLineScroll) {
+ // let word = $(document.querySelector(".word"));
+ // $("#words").prepend(
+ // `
`
+ // );
+ // lineTransition = true;
+ // $("#words .smoothScroller").animate(
+ // {
+ // height: 0,
+ // },
+ // 100,
+ // () => {
+ // $("#words .smoothScroller").remove();
+ // lineTransition = false;
+ // $(this).remove();
+ // activeWordTop = document.querySelector("#words .active")
+ // .offsetTop;
+ // }
+ // );
+ // }
+ // toHide.forEach((el) => el.remove());
+ }
+ currentTestLine++;
+ }
+ } //end of line wrap
+ if (activeFunBox === "layoutfluid" && config.mode !== "time") {
+ const layouts = ["qwerty", "dvorak", "colemak"];
+ let index = 0;
+ let outof = wordsList.length;
+ index = Math.floor((inputHistory.length + 1) / (outof / 3));
+ if (config.layout !== layouts[index] && layouts[index] !== undefined) {
+ showNotification(`--- !!! ${layouts[index]} !!! ---`, 3000);
+ }
+ setLayout(layouts[index]);
+ setKeymapLayout(layouts[index]);
+ updateHighlightedKeymapKey();
+ settingsGroups.layout.updateButton();
+ }
+ if (config.blindMode) $("#words .word.active letter").addClass("correct");
+ // document
+ // .querySelector("#words .word.active")
+ // .setAttribute("input", currentInput);
+ dontInsertSpace = true;
+ if (currentWord == currentInput) {
+ //correct word
+ if (
+ paceCaret !== null &&
+ paceCaret.wordsStatus[currentWordIndex] === true &&
+ !config.blindMode
+ ) {
+ paceCaret.wordsStatus[currentWordIndex] = undefined;
+ paceCaret.correction -= currentWord.length + 1;
+ }
+ accuracyStats.correct++;
+ inputHistory.push(currentInput);
+ currentInput = "";
+ currentWordIndex++;
+ currentWordElementIndex++;
+ updateActiveElement();
+ updateCaretPosition();
+ currentKeypress.count++;
+ currentKeypress.words.push(currentWordIndex);
+ playClickSound();
+ } else {
+ //incorrect word
+ if (
+ paceCaret !== null &&
+ paceCaret.wordsStatus[currentWordIndex] === undefined &&
+ !config.blindMode
+ ) {
+ paceCaret.wordsStatus[currentWordIndex] = true;
+ paceCaret.correction += currentWord.length + 1;
+ }
+ if (!config.playSoundOnError || config.blindMode) {
+ playClickSound();
+ } else {
+ playErrorSound();
+ }
+ accuracyStats.incorrect++;
+ let cil = currentInput.length;
+ if (cil < wordsList[currentWordIndex].length) {
+ if (cil >= currentCorrected.length) {
+ currentCorrected += "_";
+ } else {
+ currentCorrected =
+ currentCorrected.substring(0, cil) +
+ "_" +
+ currentCorrected.substring(cil + 1);
+ }
+ }
+ if (config.stopOnError != "off") {
+ if (config.difficulty == "expert" || config.difficulty == "master") {
+ //failed due to diff when pressing space
+ inputHistory.push(currentInput);
+ correctedHistory.push(currentCorrected);
+ lastSecondNotRound = true;
+ showResult(true);
+ // if (!afkDetected) {
+ let testNow = Date.now();
+ let testSeconds = roundTo2((testNow - testStart) / 1000);
+ incompleteTestSeconds += testSeconds;
+ restartCount++;
+ // }
+ return;
+ }
+ return;
+ }
+ inputHistory.push(currentInput);
+ highlightBadWord(currentWordElementIndex, !config.blindMode);
+ currentInput = "";
+ currentWordIndex++;
+ currentWordElementIndex++;
+ if (config.difficulty == "expert" || config.difficulty == "master") {
+ correctedHistory.push(currentCorrected);
+ currentCorrected = "";
+ //submitted last word incorrect and failed test
+ lastSecondNotRound = true;
+ showResult(true);
+ // if (!afkDetected) {
+ let testNow = Date.now();
+ let testSeconds = roundTo2((testNow - testStart) / 1000);
+ incompleteTestSeconds += testSeconds;
+ restartCount++;
+ // }
+ return;
+ } else if (currentWordIndex == wordsList.length) {
+ //submitted last word that is incorrect
+ lastSecondNotRound = true;
+ showResult();
+ return;
+ }
+ updateActiveElement();
+ updateCaretPosition();
+ currentKeypress.count++;
+ currentKeypress.words.push(currentWordIndex);
+ }
+ correctedHistory.push(currentCorrected);
+ currentCorrected = "";
+ if (config.keymapMode === "react") {
+ flashPressedKeymapKey(event.code, true);
+ } else if (config.keymapMode === "next") {
+ updateHighlightedKeymapKey();
+ }
+ if (
+ config.mode === "words" ||
+ config.mode === "custom" ||
+ config.mode === "quote"
+ ) {
+ updateTimer();
+ }
+ // if (config.showAllLines) {
+ // if (config.mode == "time") {
+ // addWord();
+ // }
+ // } else {
+ if (
+ config.mode == "time" ||
+ config.mode == "words" ||
+ config.mode == "custom"
+ ) {
+ addWord();
+ }
+ // }
+ }
+ }
+});
+
//keypresses for the test, using different method to be more responsive
$(document).keydown(function (event) {
if (!$("#wordsInput").is(":focus")) return;
if (
[
"Tab",
- " ",
"ContextMenu",
"Escape",
"Shift",
@@ -4612,6 +4983,17 @@ $(document).keydown(function (event) {
].includes(event.key)
)
return;
+ if (event.key === " ") {
+ if (config.difficulty !== "normal") {
+ if (dontInsertSpace) {
+ dontInsertSpace = false;
+ return;
+ }
+ } else {
+ return;
+ }
+ }
+
if (event.key.length > 1) return;
if (/F\d+/.test(event.key)) return;
if (/Numpad/.test(event.key)) return;
@@ -4805,376 +5187,6 @@ window.addEventListener("beforeunload", (event) => {
}
});
-//handle keyboard events
-$(document).keydown((event) => {
- if (!resultVisible) {
- let now = performance.now();
- let diff = Math.abs(keypressStats.spacing.current - now);
- if (keypressStats.spacing.current !== -1) {
- keypressStats.spacing.array.push(diff);
- }
- keypressStats.spacing.current = now;
- }
-
- //tab
- if (
- (event.key == "Tab" && !config.swapEscAndTab) ||
- (event.key == "Escape" && config.swapEscAndTab)
- ) {
- if (
- !event.ctrlKey &&
- config.quickTab &&
- !$(".pageLogin").hasClass("active") &&
- !resultCalculating &&
- $("#commandLineWrapper").hasClass("hidden") &&
- $("#simplePopupWrapper").hasClass("hidden")
- ) {
- event.preventDefault();
- if ($(".pageTest").hasClass("active")) {
- if (
- (config.mode === "words" && config.words < 1000) ||
- (config.mode === "time" && config.time < 3600) ||
- config.mode === "quote" ||
- (config.mode === "custom" &&
- customTextIsRandom &&
- customTextWordCount < 1000) ||
- (config.mode === "custom" &&
- !customTextIsRandom &&
- customText.length < 1000)
- ) {
- if (testActive) {
- let testNow = Date.now();
- let testSeconds = roundTo2((testNow - testStart) / 1000);
- incompleteTestSeconds += testSeconds;
- restartCount++;
- }
- restartTest();
- } else {
- showNotification("Quick restart disabled for long tests", 2000);
- }
- } else {
- changePage("test");
- }
- }
- }
-
- //only for the typing test
- if ($("#wordsInput").is(":focus")) {
- const isBackspace =
- event.key === "Backspace" ||
- (config.capsLockBackspace && event.key === "CapsLock");
- if (isBackspace) {
- event.preventDefault();
- if (!testActive) return;
- if (
- currentInput == "" &&
- inputHistory.length > 0 &&
- currentWordElementIndex > 0
- ) {
- if (
- (inputHistory[currentWordIndex - 1] ==
- wordsList[currentWordIndex - 1] &&
- !config.freedomMode) ||
- $($(".word")[currentWordIndex - 1]).hasClass("hidden")
- ) {
- return;
- } else {
- if (config.confidenceMode === "on" || config.confidenceMode === "max")
- return;
- if (event["ctrlKey"] || event["altKey"]) {
- currentInput = "";
- inputHistory.pop();
- correctedHistory.pop();
- } else {
- currentInput = inputHistory.pop();
- currentCorrected = correctedHistory.pop();
- }
- currentWordIndex--;
- currentWordElementIndex--;
- updateActiveElement();
- compareInput(!config.blindMode);
- }
- } else {
- if (config.confidenceMode === "max") return;
- if (event["ctrlKey"] || event["altKey"]) {
- currentInput = "";
- } else {
- currentInput = currentInput.substring(0, currentInput.length - 1);
- }
- compareInput(!config.blindMode);
- }
- playClickSound();
- if (config.keymapMode === "react") {
- flashPressedKeymapKey(event.code, true);
- } else if (config.keymapMode === "next") {
- updateHighlightedKeymapKey();
- }
- updateCaretPosition();
- }
- //space
- if (event.key === " ") {
- if (!testActive) return;
- if (currentInput == "") return;
- event.preventDefault();
- let currentWord = wordsList[currentWordIndex];
- // if (config.mode == "time") {
- if (!config.showAllLines || config.mode == "time") {
- // let currentTop = Math.floor($($("#words .word")[currentWordIndex]).position().top);
- // let nextTop = Math.floor($($("#words .word")[currentWordIndex + 1]).position().top);
- if (config.stopOnError != "off") {
- if (currentWord !== currentInput) return;
- }
-
- let currentTop = Math.floor(
- document.querySelectorAll("#words .word")[currentWordElementIndex]
- .offsetTop
- );
- let nextTop;
- try {
- nextTop = Math.floor(
- document.querySelectorAll("#words .word")[
- currentWordElementIndex + 1
- ].offsetTop
- );
- } catch (e) {
- nextTop = 0;
- }
-
- if ((nextTop > currentTop || activeWordJumped) && !lineTransition) {
- //last word of the line
- if (currentTestLine > 0) {
- let hideBound = currentTop;
- if (activeWordJumped) {
- hideBound = activeWordTopBeforeJump;
- }
- activeWordJumped = false;
-
- let toHide = [];
- let wordElements = $("#words .word");
- for (let i = 0; i < currentWordElementIndex + 1; i++) {
- if ($(wordElements[i]).hasClass("hidden")) continue;
- // let forWordTop = Math.floor($(wordElements[i]).position().top);
- let forWordTop = Math.floor(wordElements[i].offsetTop);
- if (forWordTop < hideBound - 10) {
- // $($("#words .word")[i]).addClass("hidden");
- toHide.push($($("#words .word")[i]));
- }
- }
- const wordHeight = $(document.querySelector(".word")).outerHeight(
- true
- );
- if (config.smoothLineScroll && toHide.length > 0) {
- lineTransition = true;
- $("#words").prepend(
- `
`
- );
- $("#words .smoothScroller").animate(
- {
- height: 0,
- },
- 125,
- () => {
- $("#words .smoothScroller").remove();
- }
- );
- $("#paceCaret").animate(
- {
- top:
- document.querySelector("#paceCaret").offsetTop - wordHeight,
- },
- 125
- );
- $("#words").animate(
- {
- marginTop: `-${wordHeight}px`,
- },
- 125,
- () => {
- activeWordTop = document.querySelector("#words .active")
- .offsetTop;
-
- currentWordElementIndex -= toHide.length;
- lineTransition = false;
- toHide.forEach((el) => el.remove());
- $("#words").css("marginTop", "0");
- }
- );
- } else {
- toHide.forEach((el) => el.remove());
- currentWordElementIndex -= toHide.length;
- $("#paceCaret").css({
- top:
- document.querySelector("#paceCaret").offsetTop - wordHeight,
- });
- }
- // if (config.smoothLineScroll) {
- // let word = $(document.querySelector(".word"));
- // $("#words").prepend(
- // `
`
- // );
- // lineTransition = true;
- // $("#words .smoothScroller").animate(
- // {
- // height: 0,
- // },
- // 100,
- // () => {
- // $("#words .smoothScroller").remove();
- // lineTransition = false;
- // $(this).remove();
- // activeWordTop = document.querySelector("#words .active")
- // .offsetTop;
- // }
- // );
- // }
- // toHide.forEach((el) => el.remove());
- }
- currentTestLine++;
- }
- } //end of line wrap
- if (activeFunBox === "layoutfluid" && config.mode !== "time") {
- const layouts = ["qwerty", "dvorak", "colemak"];
- let index = 0;
- let outof = wordsList.length;
- index = Math.floor((inputHistory.length + 1) / (outof / 3));
- if (config.layout !== layouts[index] && layouts[index] !== undefined) {
- showNotification(`--- !!! ${layouts[index]} !!! ---`, 3000);
- }
- setLayout(layouts[index]);
- setKeymapLayout(layouts[index]);
- updateHighlightedKeymapKey();
- settingsGroups.layout.updateButton();
- }
- if (config.blindMode) $("#words .word.active letter").addClass("correct");
- // document
- // .querySelector("#words .word.active")
- // .setAttribute("input", currentInput);
- if (currentWord == currentInput) {
- //correct word
- if (
- paceCaret !== null &&
- paceCaret.wordsStatus[currentWordIndex] === true &&
- !config.blindMode
- ) {
- paceCaret.wordsStatus[currentWordIndex] = undefined;
- paceCaret.correction -= currentWord.length + 1;
- }
- accuracyStats.correct++;
- inputHistory.push(currentInput);
- currentInput = "";
- currentWordIndex++;
- currentWordElementIndex++;
- updateActiveElement();
- updateCaretPosition();
- currentKeypress.count++;
- currentKeypress.words.push(currentWordIndex);
- playClickSound();
- } else {
- //incorrect word
- if (
- paceCaret !== null &&
- paceCaret.wordsStatus[currentWordIndex] === undefined &&
- !config.blindMode
- ) {
- paceCaret.wordsStatus[currentWordIndex] = true;
- paceCaret.correction += currentWord.length + 1;
- }
- if (!config.playSoundOnError || config.blindMode) {
- playClickSound();
- } else {
- playErrorSound();
- }
- accuracyStats.incorrect++;
- let cil = currentInput.length;
- if (cil < wordsList[currentWordIndex].length) {
- if (cil >= currentCorrected.length) {
- currentCorrected += "_";
- } else {
- currentCorrected =
- currentCorrected.substring(0, cil) +
- "_" +
- currentCorrected.substring(cil + 1);
- }
- }
- if (config.stopOnError != "off") {
- if (config.difficulty == "expert" || config.difficulty == "master") {
- //failed due to diff when pressing space
- inputHistory.push(currentInput);
- correctedHistory.push(currentCorrected);
- lastSecondNotRound = true;
- showResult(true);
- // if (!afkDetected) {
- let testNow = Date.now();
- let testSeconds = roundTo2((testNow - testStart) / 1000);
- incompleteTestSeconds += testSeconds;
- restartCount++;
- // }
- return;
- }
- return;
- }
- inputHistory.push(currentInput);
- highlightBadWord(currentWordElementIndex, !config.blindMode);
- currentInput = "";
- currentWordIndex++;
- currentWordElementIndex++;
- if (config.difficulty == "expert" || config.difficulty == "master") {
- correctedHistory.push(currentCorrected);
- currentCorrected = "";
- //submitted last word incorrect and failed test
- lastSecondNotRound = true;
- showResult(true);
- // if (!afkDetected) {
- let testNow = Date.now();
- let testSeconds = roundTo2((testNow - testStart) / 1000);
- incompleteTestSeconds += testSeconds;
- restartCount++;
- // }
- return;
- } else if (currentWordIndex == wordsList.length) {
- //submitted last word that is incorrect
- lastSecondNotRound = true;
- showResult();
- return;
- }
- updateActiveElement();
- updateCaretPosition();
- currentKeypress.count++;
- currentKeypress.words.push(currentWordIndex);
- }
- correctedHistory.push(currentCorrected);
- currentCorrected = "";
- if (config.keymapMode === "react") {
- flashPressedKeymapKey(event.code, true);
- } else if (config.keymapMode === "next") {
- updateHighlightedKeymapKey();
- }
- if (
- config.mode === "words" ||
- config.mode === "custom" ||
- config.mode === "quote"
- ) {
- updateTimer();
- }
- // if (config.showAllLines) {
- // if (config.mode == "time") {
- // addWord();
- // }
- // } else {
- if (
- config.mode == "time" ||
- config.mode == "words" ||
- config.mode == "custom"
- ) {
- addWord();
- }
- // }
- }
- }
-});
-
if (firebase.app().options.projectId === "monkey-type-dev-67af4") {
$("#top .logo .bottom").text("monkey-dev");
$("head title").text("Monkey Dev");