diff --git a/data.json b/data.json
index 930574f1..9e050737 100644
--- a/data.json
+++ b/data.json
@@ -22,7 +22,12 @@
{
"name":"黑色全屏",
"url":"/lib/tools/黑色全屏/",
- "type":"屏幕工具"
+ "type":"测试工具"
+ },
+ {
+ "name":"在线键盘鼠标测试",
+ "url":"/lib/tools/keyboard-mouse-tester/",
+ "type":"测试工具"
},
{
"name":"字符生成图片",
@@ -44,6 +49,11 @@
"url":"/lib/tools/rust-course/",
"type":"文档手册"
},
+ {
+ "name":"锈书(镜像)",
+ "url":"/lib/tools/rusty-book/",
+ "type":"文档手册"
+ },
{
"name":"狗屁不通文章生成器",
"url":"/lib/tools/BullshitGenerator/",
diff --git a/js/api.js b/js/api.js
index 0f43bcb3..6e2d7a41 100644
--- a/js/api.js
+++ b/js/api.js
@@ -43,20 +43,30 @@ var classify = [{
}]
}, {
"id": 3,
- "name": "软件模拟",
+ "name": "测试工具",
"list": [{
- "name": "在线 x86 虚拟机",
- "url": "/incert/?link=/lib/tools/v86/",
+ "name": "黑色全屏",
+ "url": "/incert/?link=/lib/tools/黑色全屏/",
"hot": 0,
"img": ""
+ }, {
+ "name": "在线键盘鼠标测试",
+ "url": "/incert/?link=/lib/tools/keyboard-mouse-tester/",
+ "hot": 1,
+ "img": ""
}]
}, {
"id": 4,
"name": "文档手册",
"list": [{
"name": "Rust 语言圣经(镜像)",
- "url": "/incert/?link=/lib/tools/rust-course/",
- "hot": 0,
+ "url": "/lib/tools/rust-course/",
+ "hot": 1,
+ "img": ""
+ }, {
+ "name": "锈书(镜像)",
+ "url": "/lib/tools/rusty-book/",
+ "hot": 1,
"img": ""
}]
}, {
@@ -70,10 +80,10 @@ var classify = [{
}]
}, {
"id": 6,
- "name": "屏幕工具",
+ "name": "软件模拟",
"list": [{
- "name": "黑色全屏",
- "url": "/incert/?link=/lib/tools/黑色全屏/",
+ "name": "在线 x86 虚拟机",
+ "url": "/incert/?link=/lib/tools/v86/",
"hot": 0,
"img": ""
}]
diff --git a/tools/keyboard-mouse-tester/README.md b/tools/keyboard-mouse-tester/README.md
new file mode 100644
index 00000000..18339167
--- /dev/null
+++ b/tools/keyboard-mouse-tester/README.md
@@ -0,0 +1,27 @@
+# Online Keyboard & Mouse Tester
+
+
hi geeks,Welcome!
+Features
+
+ - Supported by any Keyboard (English Layout)
+ - Both the down stroke and the up stroke are highlighted in different colors.
+ - Display the name of the pressed KEY
+ - Differentiate between duplicate keys (SHIFT,ALT,CTRL,ENTER)
+ - Total 106 different keys test
+ - Available : Mouse Left,RIght,Middle key & Scroll Up,Scroll Down tests
+ - User friendly UI
+
+
+
+## MAIN PAGE:
+
+
+## WORKING PROCESS:
+
+
+
+
+
+
+
+
diff --git a/tools/keyboard-mouse-tester/css/dark.min.css b/tools/keyboard-mouse-tester/css/dark.min.css
new file mode 100644
index 00000000..e1ba6383
--- /dev/null
+++ b/tools/keyboard-mouse-tester/css/dark.min.css
@@ -0,0 +1 @@
+.swal2-popup.swal2-toast{flex-direction:row;align-items:center;width:auto;padding:.625em;overflow-y:hidden;background:#19191a;box-shadow:0 0 .625em #d9d9d9}.swal2-popup.swal2-toast .swal2-header{flex-direction:row;padding:0}.swal2-popup.swal2-toast .swal2-title{flex-grow:1;justify-content:flex-start;margin:0 .6em;font-size:1em}.swal2-popup.swal2-toast .swal2-footer{margin:.5em 0 0;padding:.5em 0 0;font-size:.8em}.swal2-popup.swal2-toast .swal2-close{position:static;width:.8em;height:.8em;line-height:.8}.swal2-popup.swal2-toast .swal2-content{justify-content:flex-start;padding:0;font-size:1em}.swal2-popup.swal2-toast .swal2-icon{width:2em;min-width:2em;height:2em;margin:0}.swal2-popup.swal2-toast .swal2-icon .swal2-icon-content{display:flex;align-items:center;font-size:1.8em;font-weight:700}@media all and (-ms-high-contrast:none),(-ms-high-contrast:active){.swal2-popup.swal2-toast .swal2-icon .swal2-icon-content{font-size:.25em}}.swal2-popup.swal2-toast .swal2-icon.swal2-success .swal2-success-ring{width:2em;height:2em}.swal2-popup.swal2-toast .swal2-icon.swal2-error [class^=swal2-x-mark-line]{top:.875em;width:1.375em}.swal2-popup.swal2-toast .swal2-icon.swal2-error [class^=swal2-x-mark-line][class$=left]{left:.3125em}.swal2-popup.swal2-toast .swal2-icon.swal2-error [class^=swal2-x-mark-line][class$=right]{right:.3125em}.swal2-popup.swal2-toast .swal2-actions{flex-basis:auto!important;width:auto;height:auto;margin:0 .3125em}.swal2-popup.swal2-toast .swal2-styled{margin:0 .3125em;padding:.3125em .625em;font-size:1em}.swal2-popup.swal2-toast .swal2-styled:focus{box-shadow:0 0 0 1px #19191a,0 0 0 3px rgba(63,126,188,.4)}.swal2-popup.swal2-toast .swal2-success{border-color:#a5dc86}.swal2-popup.swal2-toast .swal2-success [class^=swal2-success-circular-line]{position:absolute;width:1.6em;height:3em;transform:rotate(45deg);border-radius:50%}.swal2-popup.swal2-toast .swal2-success [class^=swal2-success-circular-line][class$=left]{top:-.8em;left:-.5em;transform:rotate(-45deg);transform-origin:2em 2em;border-radius:4em 0 0 4em}.swal2-popup.swal2-toast .swal2-success [class^=swal2-success-circular-line][class$=right]{top:-.25em;left:.9375em;transform-origin:0 1.5em;border-radius:0 4em 4em 0}.swal2-popup.swal2-toast .swal2-success .swal2-success-ring{width:2em;height:2em}.swal2-popup.swal2-toast .swal2-success .swal2-success-fix{top:0;left:.4375em;width:.4375em;height:2.6875em}.swal2-popup.swal2-toast .swal2-success [class^=swal2-success-line]{height:.3125em}.swal2-popup.swal2-toast .swal2-success [class^=swal2-success-line][class$=tip]{top:1.125em;left:.1875em;width:.75em}.swal2-popup.swal2-toast .swal2-success [class^=swal2-success-line][class$=long]{top:.9375em;right:.1875em;width:1.375em}.swal2-popup.swal2-toast .swal2-success.swal2-icon-show .swal2-success-line-tip{-webkit-animation:swal2-toast-animate-success-line-tip .75s;animation:swal2-toast-animate-success-line-tip .75s}.swal2-popup.swal2-toast .swal2-success.swal2-icon-show .swal2-success-line-long{-webkit-animation:swal2-toast-animate-success-line-long .75s;animation:swal2-toast-animate-success-line-long .75s}.swal2-popup.swal2-toast.swal2-show{-webkit-animation:swal2-toast-show .5s;animation:swal2-toast-show .5s}.swal2-popup.swal2-toast.swal2-hide{-webkit-animation:swal2-toast-hide .1s forwards;animation:swal2-toast-hide .1s forwards}.swal2-container{display:flex;position:fixed;z-index:1060;top:0;right:0;bottom:0;left:0;flex-direction:row;align-items:center;justify-content:center;padding:.625em;overflow-x:hidden;transition:background-color .1s;-webkit-overflow-scrolling:touch}.swal2-container.swal2-backdrop-show,.swal2-container.swal2-noanimation{background:rgba(25,25,26,.75)}.swal2-container.swal2-backdrop-hide{background:0 0!important}.swal2-container.swal2-top{align-items:flex-start}.swal2-container.swal2-top-left,.swal2-container.swal2-top-start{align-items:flex-start;justify-content:flex-start}.swal2-container.swal2-top-end,.swal2-container.swal2-top-right{align-items:flex-start;justify-content:flex-end}.swal2-container.swal2-center{align-items:center}.swal2-container.swal2-center-left,.swal2-container.swal2-center-start{align-items:center;justify-content:flex-start}.swal2-container.swal2-center-end,.swal2-container.swal2-center-right{align-items:center;justify-content:flex-end}.swal2-container.swal2-bottom{align-items:flex-end}.swal2-container.swal2-bottom-left,.swal2-container.swal2-bottom-start{align-items:flex-end;justify-content:flex-start}.swal2-container.swal2-bottom-end,.swal2-container.swal2-bottom-right{align-items:flex-end;justify-content:flex-end}.swal2-container.swal2-bottom-end>:first-child,.swal2-container.swal2-bottom-left>:first-child,.swal2-container.swal2-bottom-right>:first-child,.swal2-container.swal2-bottom-start>:first-child,.swal2-container.swal2-bottom>:first-child{margin-top:auto}.swal2-container.swal2-grow-fullscreen>.swal2-modal{display:flex!important;flex:1;align-self:stretch;justify-content:center}.swal2-container.swal2-grow-row>.swal2-modal{display:flex!important;flex:1;align-content:center;justify-content:center}.swal2-container.swal2-grow-column{flex:1;flex-direction:column}.swal2-container.swal2-grow-column.swal2-bottom,.swal2-container.swal2-grow-column.swal2-center,.swal2-container.swal2-grow-column.swal2-top{align-items:center}.swal2-container.swal2-grow-column.swal2-bottom-left,.swal2-container.swal2-grow-column.swal2-bottom-start,.swal2-container.swal2-grow-column.swal2-center-left,.swal2-container.swal2-grow-column.swal2-center-start,.swal2-container.swal2-grow-column.swal2-top-left,.swal2-container.swal2-grow-column.swal2-top-start{align-items:flex-start}.swal2-container.swal2-grow-column.swal2-bottom-end,.swal2-container.swal2-grow-column.swal2-bottom-right,.swal2-container.swal2-grow-column.swal2-center-end,.swal2-container.swal2-grow-column.swal2-center-right,.swal2-container.swal2-grow-column.swal2-top-end,.swal2-container.swal2-grow-column.swal2-top-right{align-items:flex-end}.swal2-container.swal2-grow-column>.swal2-modal{display:flex!important;flex:1;align-content:center;justify-content:center}.swal2-container.swal2-no-transition{transition:none!important}.swal2-container:not(.swal2-top):not(.swal2-top-start):not(.swal2-top-end):not(.swal2-top-left):not(.swal2-top-right):not(.swal2-center-start):not(.swal2-center-end):not(.swal2-center-left):not(.swal2-center-right):not(.swal2-bottom):not(.swal2-bottom-start):not(.swal2-bottom-end):not(.swal2-bottom-left):not(.swal2-bottom-right):not(.swal2-grow-fullscreen)>.swal2-modal{margin:auto}@media all and (-ms-high-contrast:none),(-ms-high-contrast:active){.swal2-container .swal2-modal{margin:0!important}}.swal2-popup{display:none;position:relative;box-sizing:border-box;flex-direction:column;justify-content:center;width:32em;max-width:100%;padding:1.25em;border:none;border-radius:.3125em;background:#19191a;font-family:inherit;font-size:1rem}.swal2-popup:focus{outline:0}.swal2-popup.swal2-loading{overflow-y:hidden}.swal2-header{display:flex;flex-direction:column;align-items:center;padding:0 1.8em}.swal2-title{position:relative;max-width:100%;margin:0 0 .4em;padding:0;color:#e1e1e1;font-size:1.875em;font-weight:600;text-align:center;text-transform:none;word-wrap:break-word}.swal2-actions{display:flex;z-index:1;box-sizing:border-box;flex-wrap:wrap;align-items:center;justify-content:center;width:100%;margin:1.25em auto 0;padding:0 1.6em}.swal2-actions:not(.swal2-loading) .swal2-styled[disabled]{opacity:.4}.swal2-actions:not(.swal2-loading) .swal2-styled:hover{background-image:linear-gradient(rgba(0,0,0,.1),rgba(0,0,0,.1))}.swal2-actions:not(.swal2-loading) .swal2-styled:active{background-image:linear-gradient(rgba(0,0,0,.2),rgba(0,0,0,.2))}.swal2-loader{display:none;align-items:center;justify-content:center;width:2.2em;height:2.2em;margin:0 1.875em;-webkit-animation:swal2-rotate-loading 1.5s linear 0s infinite normal;animation:swal2-rotate-loading 1.5s linear 0s infinite normal;border-width:.25em;border-style:solid;border-radius:100%;border-color:#3085d6 transparent #3085d6 transparent}.swal2-styled{margin:.3125em;padding:.625em 2em;box-shadow:none;font-weight:500}.swal2-styled:not([disabled]){cursor:pointer}.swal2-styled.swal2-confirm{border:0;border-radius:.25em;background:initial;background-color:#3085d6;color:#fff;font-size:1.0625em}.swal2-styled.swal2-deny{border:0;border-radius:.25em;background:initial;background-color:#dd6b55;color:#fff;font-size:1.0625em}.swal2-styled.swal2-cancel{border:0;border-radius:.25em;background:initial;background-color:#aaa;color:#fff;font-size:1.0625em}.swal2-styled:focus{outline:0;box-shadow:0 0 0 1px #19191a,0 0 0 3px rgba(63,126,188,.4)}.swal2-styled::-moz-focus-inner{border:0}.swal2-footer{justify-content:center;margin:1.25em 0 0;padding:1em 0 0;border-top:1px solid #555;color:#bbb;font-size:1em}.swal2-timer-progress-bar-container{position:absolute;right:0;bottom:0;left:0;height:.25em;overflow:hidden;border-bottom-right-radius:.3125em;border-bottom-left-radius:.3125em}.swal2-timer-progress-bar{width:100%;height:.25em;background:rgba(225,225,225,.6)}.swal2-image{max-width:100%;margin:1.25em auto}.swal2-close{position:absolute;z-index:2;top:0;right:0;align-items:center;justify-content:center;width:1.2em;height:1.2em;padding:0;overflow:hidden;transition:color .1s ease-out;border:none;border-radius:0;background:0 0;color:#ccc;font-family:serif;font-size:2.5em;line-height:1.2;cursor:pointer}.swal2-close:hover{transform:none;background:0 0;color:#f27474}.swal2-close::-moz-focus-inner{border:0}.swal2-content{z-index:1;justify-content:center;margin:0;padding:0 1.6em;color:#e1e1e1;font-size:1.125em;font-weight:400;line-height:normal;text-align:center;word-wrap:break-word}.swal2-checkbox,.swal2-file,.swal2-input,.swal2-radio,.swal2-select,.swal2-textarea{margin:1em auto}.swal2-file,.swal2-input,.swal2-textarea{box-sizing:border-box;width:100%;transition:border-color .3s,box-shadow .3s;border:1px solid #d9d9d9;border-radius:.1875em;background:#323234;box-shadow:inset 0 1px 1px rgba(0,0,0,.06);color:#e1e1e1;font-size:1.125em}.swal2-file.swal2-inputerror,.swal2-input.swal2-inputerror,.swal2-textarea.swal2-inputerror{border-color:#f27474!important;box-shadow:0 0 2px #f27474!important}.swal2-file:focus,.swal2-input:focus,.swal2-textarea:focus{border:1px solid #b4dbed;outline:0;box-shadow:0 0 3px #c4e6f5}.swal2-file::-moz-placeholder,.swal2-input::-moz-placeholder,.swal2-textarea::-moz-placeholder{color:#ccc}.swal2-file:-ms-input-placeholder,.swal2-input:-ms-input-placeholder,.swal2-textarea:-ms-input-placeholder{color:#ccc}.swal2-file::placeholder,.swal2-input::placeholder,.swal2-textarea::placeholder{color:#ccc}.swal2-range{margin:1em auto;background:#19191a}.swal2-range input{width:80%}.swal2-range output{width:20%;color:#e1e1e1;font-weight:600;text-align:center}.swal2-range input,.swal2-range output{height:2.625em;padding:0;font-size:1.125em;line-height:2.625em}.swal2-input{height:2.625em;padding:0 .75em}.swal2-input[type=number]{max-width:10em}.swal2-file{background:#323234;font-size:1.125em}.swal2-textarea{height:6.75em;padding:.75em}.swal2-select{min-width:50%;max-width:100%;padding:.375em .625em;background:#323234;color:#e1e1e1;font-size:1.125em}.swal2-checkbox,.swal2-radio{align-items:center;justify-content:center;background:#19191a;color:#e1e1e1}.swal2-checkbox label,.swal2-radio label{margin:0 .6em;font-size:1.125em}.swal2-checkbox input,.swal2-radio input{margin:0 .4em}.swal2-validation-message{display:none;align-items:center;justify-content:center;padding:.625em;overflow:hidden;background:#323234;color:#e1e1e1;font-size:1em;font-weight:300}.swal2-validation-message::before{content:'!';display:inline-block;width:1.5em;min-width:1.5em;height:1.5em;margin:0 .625em;border-radius:50%;background-color:#f27474;color:#fff;font-weight:600;line-height:1.5em;text-align:center}.swal2-icon{position:relative;box-sizing:content-box;justify-content:center;width:5em;height:5em;margin:1.25em auto 1.875em;border:.25em solid transparent;border-radius:50%;font-family:inherit;line-height:5em;cursor:default;-webkit-user-select:none;-moz-user-select:none;-ms-user-select:none;user-select:none}.swal2-icon .swal2-icon-content{display:flex;align-items:center;font-size:3.75em}.swal2-icon.swal2-error{border-color:#f27474;color:#f27474}.swal2-icon.swal2-error .swal2-x-mark{position:relative;flex-grow:1}.swal2-icon.swal2-error [class^=swal2-x-mark-line]{display:block;position:absolute;top:2.3125em;width:2.9375em;height:.3125em;border-radius:.125em;background-color:#f27474}.swal2-icon.swal2-error [class^=swal2-x-mark-line][class$=left]{left:1.0625em;transform:rotate(45deg)}.swal2-icon.swal2-error [class^=swal2-x-mark-line][class$=right]{right:1em;transform:rotate(-45deg)}.swal2-icon.swal2-error.swal2-icon-show{-webkit-animation:swal2-animate-error-icon .5s;animation:swal2-animate-error-icon .5s}.swal2-icon.swal2-error.swal2-icon-show .swal2-x-mark{-webkit-animation:swal2-animate-error-x-mark .5s;animation:swal2-animate-error-x-mark .5s}.swal2-icon.swal2-warning{border-color:#facea8;color:#f8bb86}.swal2-icon.swal2-info{border-color:#9de0f6;color:#3fc3ee}.swal2-icon.swal2-question{border-color:#c9dae1;color:#87adbd}.swal2-icon.swal2-success{border-color:#a5dc86;color:#a5dc86}.swal2-icon.swal2-success [class^=swal2-success-circular-line]{position:absolute;width:3.75em;height:7.5em;transform:rotate(45deg);border-radius:50%}.swal2-icon.swal2-success [class^=swal2-success-circular-line][class$=left]{top:-.4375em;left:-2.0635em;transform:rotate(-45deg);transform-origin:3.75em 3.75em;border-radius:7.5em 0 0 7.5em}.swal2-icon.swal2-success [class^=swal2-success-circular-line][class$=right]{top:-.6875em;left:1.875em;transform:rotate(-45deg);transform-origin:0 3.75em;border-radius:0 7.5em 7.5em 0}.swal2-icon.swal2-success .swal2-success-ring{position:absolute;z-index:2;top:-.25em;left:-.25em;box-sizing:content-box;width:100%;height:100%;border:.25em solid rgba(165,220,134,.3);border-radius:50%}.swal2-icon.swal2-success .swal2-success-fix{position:absolute;z-index:1;top:.5em;left:1.625em;width:.4375em;height:5.625em;transform:rotate(-45deg)}.swal2-icon.swal2-success [class^=swal2-success-line]{display:block;position:absolute;z-index:2;height:.3125em;border-radius:.125em;background-color:#a5dc86}.swal2-icon.swal2-success [class^=swal2-success-line][class$=tip]{top:2.875em;left:.8125em;width:1.5625em;transform:rotate(45deg)}.swal2-icon.swal2-success [class^=swal2-success-line][class$=long]{top:2.375em;right:.5em;width:2.9375em;transform:rotate(-45deg)}.swal2-icon.swal2-success.swal2-icon-show .swal2-success-line-tip{-webkit-animation:swal2-animate-success-line-tip .75s;animation:swal2-animate-success-line-tip .75s}.swal2-icon.swal2-success.swal2-icon-show .swal2-success-line-long{-webkit-animation:swal2-animate-success-line-long .75s;animation:swal2-animate-success-line-long .75s}.swal2-icon.swal2-success.swal2-icon-show .swal2-success-circular-line-right{-webkit-animation:swal2-rotate-success-circular-line 4.25s ease-in;animation:swal2-rotate-success-circular-line 4.25s ease-in}.swal2-progress-steps{align-items:center;margin:0 0 1.25em;padding:0;background:inherit;font-weight:600}.swal2-progress-steps li{display:inline-block;position:relative}.swal2-progress-steps .swal2-progress-step{z-index:20;width:2em;height:2em;border-radius:2em;background:#3085d6;color:#fff;line-height:2em;text-align:center}.swal2-progress-steps .swal2-progress-step.swal2-active-progress-step{background:#3085d6}.swal2-progress-steps .swal2-progress-step.swal2-active-progress-step~.swal2-progress-step{background:#58585b;color:#fff}.swal2-progress-steps .swal2-progress-step.swal2-active-progress-step~.swal2-progress-step-line{background:#58585b}.swal2-progress-steps .swal2-progress-step-line{z-index:10;width:2.5em;height:.4em;margin:0 -1px;background:#3085d6}[class^=swal2]{-webkit-tap-highlight-color:transparent}.swal2-show{-webkit-animation:swal2-show .3s;animation:swal2-show .3s}.swal2-hide{-webkit-animation:swal2-hide .15s forwards;animation:swal2-hide .15s forwards}.swal2-noanimation{transition:none}.swal2-scrollbar-measure{position:absolute;top:-9999px;width:50px;height:50px;overflow:scroll}.swal2-rtl .swal2-close{right:auto;left:0}.swal2-rtl .swal2-timer-progress-bar{right:0;left:auto}@supports (-ms-accelerator:true){.swal2-range input{width:100%!important}.swal2-range output{display:none}}@media all and (-ms-high-contrast:none),(-ms-high-contrast:active){.swal2-range input{width:100%!important}.swal2-range output{display:none}}@-moz-document url-prefix(){.swal2-close:focus{outline:2px solid rgba(63,126,188,.4)}}@-webkit-keyframes swal2-toast-show{0%{transform:translateY(-.625em) rotateZ(2deg)}33%{transform:translateY(0) rotateZ(-2deg)}66%{transform:translateY(.3125em) rotateZ(2deg)}100%{transform:translateY(0) rotateZ(0)}}@keyframes swal2-toast-show{0%{transform:translateY(-.625em) rotateZ(2deg)}33%{transform:translateY(0) rotateZ(-2deg)}66%{transform:translateY(.3125em) rotateZ(2deg)}100%{transform:translateY(0) rotateZ(0)}}@-webkit-keyframes swal2-toast-hide{100%{transform:rotateZ(1deg);opacity:0}}@keyframes swal2-toast-hide{100%{transform:rotateZ(1deg);opacity:0}}@-webkit-keyframes swal2-toast-animate-success-line-tip{0%{top:.5625em;left:.0625em;width:0}54%{top:.125em;left:.125em;width:0}70%{top:.625em;left:-.25em;width:1.625em}84%{top:1.0625em;left:.75em;width:.5em}100%{top:1.125em;left:.1875em;width:.75em}}@keyframes swal2-toast-animate-success-line-tip{0%{top:.5625em;left:.0625em;width:0}54%{top:.125em;left:.125em;width:0}70%{top:.625em;left:-.25em;width:1.625em}84%{top:1.0625em;left:.75em;width:.5em}100%{top:1.125em;left:.1875em;width:.75em}}@-webkit-keyframes swal2-toast-animate-success-line-long{0%{top:1.625em;right:1.375em;width:0}65%{top:1.25em;right:.9375em;width:0}84%{top:.9375em;right:0;width:1.125em}100%{top:.9375em;right:.1875em;width:1.375em}}@keyframes swal2-toast-animate-success-line-long{0%{top:1.625em;right:1.375em;width:0}65%{top:1.25em;right:.9375em;width:0}84%{top:.9375em;right:0;width:1.125em}100%{top:.9375em;right:.1875em;width:1.375em}}@-webkit-keyframes swal2-show{0%{transform:scale(.7)}45%{transform:scale(1.05)}80%{transform:scale(.95)}100%{transform:scale(1)}}@keyframes swal2-show{0%{transform:scale(.7)}45%{transform:scale(1.05)}80%{transform:scale(.95)}100%{transform:scale(1)}}@-webkit-keyframes swal2-hide{0%{transform:scale(1);opacity:1}100%{transform:scale(.5);opacity:0}}@keyframes swal2-hide{0%{transform:scale(1);opacity:1}100%{transform:scale(.5);opacity:0}}@-webkit-keyframes swal2-animate-success-line-tip{0%{top:1.1875em;left:.0625em;width:0}54%{top:1.0625em;left:.125em;width:0}70%{top:2.1875em;left:-.375em;width:3.125em}84%{top:3em;left:1.3125em;width:1.0625em}100%{top:2.8125em;left:.8125em;width:1.5625em}}@keyframes swal2-animate-success-line-tip{0%{top:1.1875em;left:.0625em;width:0}54%{top:1.0625em;left:.125em;width:0}70%{top:2.1875em;left:-.375em;width:3.125em}84%{top:3em;left:1.3125em;width:1.0625em}100%{top:2.8125em;left:.8125em;width:1.5625em}}@-webkit-keyframes swal2-animate-success-line-long{0%{top:3.375em;right:2.875em;width:0}65%{top:3.375em;right:2.875em;width:0}84%{top:2.1875em;right:0;width:3.4375em}100%{top:2.375em;right:.5em;width:2.9375em}}@keyframes swal2-animate-success-line-long{0%{top:3.375em;right:2.875em;width:0}65%{top:3.375em;right:2.875em;width:0}84%{top:2.1875em;right:0;width:3.4375em}100%{top:2.375em;right:.5em;width:2.9375em}}@-webkit-keyframes swal2-rotate-success-circular-line{0%{transform:rotate(-45deg)}5%{transform:rotate(-45deg)}12%{transform:rotate(-405deg)}100%{transform:rotate(-405deg)}}@keyframes swal2-rotate-success-circular-line{0%{transform:rotate(-45deg)}5%{transform:rotate(-45deg)}12%{transform:rotate(-405deg)}100%{transform:rotate(-405deg)}}@-webkit-keyframes swal2-animate-error-x-mark{0%{margin-top:1.625em;transform:scale(.4);opacity:0}50%{margin-top:1.625em;transform:scale(.4);opacity:0}80%{margin-top:-.375em;transform:scale(1.15)}100%{margin-top:0;transform:scale(1);opacity:1}}@keyframes swal2-animate-error-x-mark{0%{margin-top:1.625em;transform:scale(.4);opacity:0}50%{margin-top:1.625em;transform:scale(.4);opacity:0}80%{margin-top:-.375em;transform:scale(1.15)}100%{margin-top:0;transform:scale(1);opacity:1}}@-webkit-keyframes swal2-animate-error-icon{0%{transform:rotateX(100deg);opacity:0}100%{transform:rotateX(0);opacity:1}}@keyframes swal2-animate-error-icon{0%{transform:rotateX(100deg);opacity:0}100%{transform:rotateX(0);opacity:1}}@-webkit-keyframes swal2-rotate-loading{0%{transform:rotate(0)}100%{transform:rotate(360deg)}}@keyframes swal2-rotate-loading{0%{transform:rotate(0)}100%{transform:rotate(360deg)}}body.swal2-shown:not(.swal2-no-backdrop):not(.swal2-toast-shown){overflow:hidden}body.swal2-height-auto{height:auto!important}body.swal2-no-backdrop .swal2-container{top:auto;right:auto;bottom:auto;left:auto;max-width:calc(100% - .625em * 2);background-color:transparent!important}body.swal2-no-backdrop .swal2-container>.swal2-modal{box-shadow:0 0 10px rgba(25,25,26,.75)}body.swal2-no-backdrop .swal2-container.swal2-top{top:0;left:50%;transform:translateX(-50%)}body.swal2-no-backdrop .swal2-container.swal2-top-left,body.swal2-no-backdrop .swal2-container.swal2-top-start{top:0;left:0}body.swal2-no-backdrop .swal2-container.swal2-top-end,body.swal2-no-backdrop .swal2-container.swal2-top-right{top:0;right:0}body.swal2-no-backdrop .swal2-container.swal2-center{top:50%;left:50%;transform:translate(-50%,-50%)}body.swal2-no-backdrop .swal2-container.swal2-center-left,body.swal2-no-backdrop .swal2-container.swal2-center-start{top:50%;left:0;transform:translateY(-50%)}body.swal2-no-backdrop .swal2-container.swal2-center-end,body.swal2-no-backdrop .swal2-container.swal2-center-right{top:50%;right:0;transform:translateY(-50%)}body.swal2-no-backdrop .swal2-container.swal2-bottom{bottom:0;left:50%;transform:translateX(-50%)}body.swal2-no-backdrop .swal2-container.swal2-bottom-left,body.swal2-no-backdrop .swal2-container.swal2-bottom-start{bottom:0;left:0}body.swal2-no-backdrop .swal2-container.swal2-bottom-end,body.swal2-no-backdrop .swal2-container.swal2-bottom-right{right:0;bottom:0}@media print{body.swal2-shown:not(.swal2-no-backdrop):not(.swal2-toast-shown){overflow-y:scroll!important}body.swal2-shown:not(.swal2-no-backdrop):not(.swal2-toast-shown)>[aria-hidden=true]{display:none}body.swal2-shown:not(.swal2-no-backdrop):not(.swal2-toast-shown) .swal2-container{position:static!important}}body.swal2-toast-shown .swal2-container{background-color:transparent}body.swal2-toast-shown .swal2-container.swal2-top{top:0;right:auto;bottom:auto;left:50%;transform:translateX(-50%)}body.swal2-toast-shown .swal2-container.swal2-top-end,body.swal2-toast-shown .swal2-container.swal2-top-right{top:0;right:0;bottom:auto;left:auto}body.swal2-toast-shown .swal2-container.swal2-top-left,body.swal2-toast-shown .swal2-container.swal2-top-start{top:0;right:auto;bottom:auto;left:0}body.swal2-toast-shown .swal2-container.swal2-center-left,body.swal2-toast-shown .swal2-container.swal2-center-start{top:50%;right:auto;bottom:auto;left:0;transform:translateY(-50%)}body.swal2-toast-shown .swal2-container.swal2-center{top:50%;right:auto;bottom:auto;left:50%;transform:translate(-50%,-50%)}body.swal2-toast-shown .swal2-container.swal2-center-end,body.swal2-toast-shown .swal2-container.swal2-center-right{top:50%;right:0;bottom:auto;left:auto;transform:translateY(-50%)}body.swal2-toast-shown .swal2-container.swal2-bottom-left,body.swal2-toast-shown .swal2-container.swal2-bottom-start{top:auto;right:auto;bottom:0;left:0}body.swal2-toast-shown .swal2-container.swal2-bottom{top:auto;right:auto;bottom:0;left:50%;transform:translateX(-50%)}body.swal2-toast-shown .swal2-container.swal2-bottom-end,body.swal2-toast-shown .swal2-container.swal2-bottom-right{top:auto;right:0;bottom:0;left:auto}body.swal2-toast-column .swal2-toast{flex-direction:column;align-items:stretch}body.swal2-toast-column .swal2-toast .swal2-actions{flex:1;align-self:stretch;height:2.2em;margin-top:.3125em}body.swal2-toast-column .swal2-toast .swal2-loading{justify-content:center}body.swal2-toast-column .swal2-toast .swal2-input{height:2em;margin:.3125em auto;font-size:1em}body.swal2-toast-column .swal2-toast .swal2-validation-message{font-size:1em}
\ No newline at end of file
diff --git a/tools/keyboard-mouse-tester/css/helvthin.otf b/tools/keyboard-mouse-tester/css/helvthin.otf
new file mode 100644
index 00000000..b1fbf233
Binary files /dev/null and b/tools/keyboard-mouse-tester/css/helvthin.otf differ
diff --git a/tools/keyboard-mouse-tester/css/style.css b/tools/keyboard-mouse-tester/css/style.css
new file mode 100644
index 00000000..74e39a70
--- /dev/null
+++ b/tools/keyboard-mouse-tester/css/style.css
@@ -0,0 +1,355 @@
+@font-face {
+ font-family: Helvetica;
+ font-style: normal;
+ font-weight: 400;
+ src: url(../css/helvthin.otf);
+}
+body {
+ margin: 0;
+ padding: 0;
+ font-family: "Helvetica";
+ background-color: #000;
+}
+header {
+ background: url(../img/background.jpg) no-repeat 50% 50%;
+ background-color: #000;
+ height: 950px;
+ overflow: auto;
+}
+.key {
+ border: 1px solid red;
+ border-radius: 8px;
+ color: red;
+ display: inline-block;
+ font-size: 18px;
+ height: 52px;
+ text-align: center;
+ vertical-align: top;
+ width: 52px;
+ margin: 5px 1px;
+ border-bottom: 2px solid red;
+}
+.keyFunc {
+ border: 1px solid red;
+ border-radius: 8px;
+ color: red;
+ display: inline-block;
+ font-size: 14px;
+ height: 35px;
+ text-align: center;
+ vertical-align: top;
+ width: 47px;
+ margin: 5px 1px;
+ border-bottom: 2px solid red;
+}
+.keyboard-body {
+ height: 650px;
+ margin: 5px auto 0;
+ width: 1264px;
+ position: relative;
+}
+.header-gap {
+ width: 1264px;
+ margin: 0 auto;
+ text-align: center;
+ padding: 16px 0 0;
+}
+.header-gap > div {
+ display: inline-block;
+ margin: 0 90px;
+}
+.keyboard-bg-blur {
+ background: rgba(0, 0, 0, 0) url(../img/background.jpg) no-repeat scroll
+ center 51%;
+ filter: blur(50px);
+ height: 100%;
+ margin: 0;
+ padding: 0;
+ position: absolute;
+ width: 100%;
+ z-index: 1;
+}
+.keyboard-bg-fade {
+ background-color: #000;
+ height: 100%;
+ opacity: 0.5;
+ position: absolute;
+ width: 100%;
+ z-index: 2;
+}
+.content {
+ height: 100%;
+ position: absolute;
+ width: 100%;
+ z-index: 3;
+}
+.keyboard-header {
+ background-color: #000;
+ color: #008b8b;
+ height: 50px;
+ overflow: hidden;
+ padding-top: 5px;
+ width: 100%;
+ border: 1px solid #8b0000;
+ border-radius: 8px;
+}
+.keyOutput {
+ border: 1px solid #008b8b;
+ border-radius: 8px;
+ color: #008b8b;
+ display: inline-block;
+ font-size: 16px;
+ height: 30px;
+ text-align: center;
+ width: 120px;
+ margin: 7px 0;
+ font-family: consolas;
+}
+.keyOutput > p {
+ margin-top: 5px;
+}
+.areaGap {
+ visibility: hidden;
+}
+.delKey {
+ font-size: 15px;
+ line-height: 0.9;
+}
+.delKey > p {
+ margin-top: 14px;
+}
+.t16 {
+ font-size: 16px;
+}
+.t16 > p {
+ margin-top: 18px;
+}
+.key.delKey.minSize > p {
+ font-size: 28px;
+ margin-top: -2px;
+}
+.key.delKey.plusKey > p {
+ font-size: 20px;
+ line-height: 0.7;
+}
+.brackets {
+ margin-left: 8px;
+ margin-right: 8px;
+}
+.gapWidth {
+ width: 2px;
+}
+.keyboard-section {
+ padding: 0 22px;
+}
+.key.backSpace > p {
+ margin: 10px;
+ transform: translateY(-26px);
+ text-align: center;
+ margin-left: 60px;
+}
+.key.backSpace {
+ font-size: 35px;
+ width: 177px;
+}
+.key.tab {
+ text-align: left;
+ width: 83px;
+}
+.key.arithmeticKey > p {
+ font-size: 20px;
+ margin-top: 16px;
+}
+.key.arithmeticKey.backslash {
+ width: 146px;
+}
+.key.plus {
+ float: right;
+ height: 116px;
+}
+.key.plus > p {
+ margin-top: 45px;
+}
+.key.caps {
+ font-size: 16px;
+ width: 105px;
+}
+.key.caps > p {
+ text-align: left;
+ margin-left: 7px;
+ margin-top: 17px;
+}
+.key.enter {
+ width: 184px;
+}
+.key.enter > p {
+ text-align: left;
+ margin-left: 112px;
+ font-size: 44px;
+ transform: translateY(-70px);
+}
+.key.shiftLeft {
+ width: 132px;
+}
+.key.shiftLeft > p,
+.key.shiftRight > p {
+ font-size: 16px;
+ margin-top: 18px;
+ text-align: left;
+ margin-left: 7px;
+}
+.key.shiftRight {
+ width: 157px;
+}
+.key.enterRight {
+ float: right;
+ height: 116px;
+}
+.key.enterRight > p {
+ font-size: 16px;
+ margin-top: 48px;
+}
+.key.ctrl1,
+.key.ctrl2 {
+ text-align: left;
+ width: 95px;
+}
+.key.cont {
+ width: 66px;
+}
+.key.cont > p {
+ margin: 14px auto 0;
+ text-align: center;
+}
+.key.arrowUp > p {
+ font-size: 26px;
+ margin-top: 9px;
+ transform: rotate(-90deg);
+}
+.key.wndw > p {
+ margin: 14px auto 0;
+ text-align: center;
+}
+.key.wndw {
+ width: 70px;
+}
+.key.alt {
+ width: 70px;
+}
+.key.space {
+ width: 325px;
+}
+.key.zero {
+ width: 112px;
+}
+.key.lclick {
+ border-radius: 55px 0 0 0;
+ height: 70px;
+ vertical-align: bottom;
+ width: 96px;
+}
+.key.rclick {
+ border-radius: 0 55px 0 0;
+ height: 70px;
+ vertical-align: bottom;
+ width: 96px;
+}
+.key.cclick {
+ border-radius: 10px;
+ height: 50px;
+ margin-top: 15px;
+ vertical-align: top;
+ width: 24px;
+}
+.key.scrollUp {
+ border-radius: 0 0 0 0;
+ height: 20px;
+ vertical-align: top;
+ width: 96px;
+}
+.key.scrollDown {
+ border-radius: 0 0 0 0;
+ height: 20px;
+ vertical-align: top;
+ width: 96px;
+}
+.key.divider {
+ border-radius: 0;
+ height: 0;
+ margin-top: 0;
+ vertical-align: top;
+ width: 24px;
+ border-color: #000;
+}
+.mouse-section {
+ text-align: center;
+ vertical-align: bottom;
+}
+.key.arrowLeft > p,
+.key.arrowRight > p {
+ font-size: 26px;
+ margin: 11px 0;
+ transform: rotate(180deg);
+}
+.key.arrowDown > p {
+ font-size: 26px;
+ margin: 14px 0 14px 5px;
+ transform: rotate(90deg);
+}
+h1 {
+ font-size: 18px;
+ margin: 0;
+ padding: 25px 0;
+}
+.key.press,
+.keyFunc.press {
+ background-color: #00ced1;
+ border-color: #00e1ef;
+ color: #000;
+ top: 0.2em;
+ box-shadow: 0 0 0 0.05em #000;
+}
+.key.active,
+.keyFunc.active {
+ background-color: #000;
+ border-color: #00e1ef;
+ color: #01c7d4;
+ top: 0.2em;
+ box-shadow: 0 0 0 0.05em #000;
+}
+.key.enter.active span,
+.key.enter.press span {
+ background-position: -24px -13px;
+}
+.sliding_text_info {
+ background-color: rgba(2, 12, 20, 0.8);
+ bottom: 0;
+ color: rgba(0, 139, 139, 0.658);
+ font-size: 14px;
+ font-weight: 700;
+ left: 0;
+ padding: 10px;
+ right: 0;
+ z-index: 200;
+ font-family: consolas;
+}
+.footer-text {
+ background-color: #000;
+ bottom: 0;
+ color: #2f4f4f;
+ font-size: 15px;
+ font-weight: 700;
+ left: 0;
+ padding: 16px;
+ position: fixed;
+ right: 0;
+ z-index: 10;
+ text-align: center;
+ font-family: consolas;
+}
+::-webkit-scrollbar {
+ width: 5px;
+}
+::-webkit-scrollbar-thumb {
+ border-radius: 1px;
+}
diff --git a/tools/keyboard-mouse-tester/img/background.jpg b/tools/keyboard-mouse-tester/img/background.jpg
new file mode 100644
index 00000000..d38be765
Binary files /dev/null and b/tools/keyboard-mouse-tester/img/background.jpg differ
diff --git a/tools/keyboard-mouse-tester/img/keyboard (5).png b/tools/keyboard-mouse-tester/img/keyboard (5).png
new file mode 100644
index 00000000..84dbdf92
Binary files /dev/null and b/tools/keyboard-mouse-tester/img/keyboard (5).png differ
diff --git a/tools/keyboard-mouse-tester/img/main_page.PNG b/tools/keyboard-mouse-tester/img/main_page.PNG
new file mode 100644
index 00000000..b1e63945
Binary files /dev/null and b/tools/keyboard-mouse-tester/img/main_page.PNG differ
diff --git a/tools/keyboard-mouse-tester/img/meta_image.PNG b/tools/keyboard-mouse-tester/img/meta_image.PNG
new file mode 100644
index 00000000..0689ee74
Binary files /dev/null and b/tools/keyboard-mouse-tester/img/meta_image.PNG differ
diff --git a/tools/keyboard-mouse-tester/img/test_process.PNG b/tools/keyboard-mouse-tester/img/test_process.PNG
new file mode 100644
index 00000000..f96d7e4c
Binary files /dev/null and b/tools/keyboard-mouse-tester/img/test_process.PNG differ
diff --git a/tools/keyboard-mouse-tester/index.html b/tools/keyboard-mouse-tester/index.html
new file mode 100644
index 00000000..88bb9c7f
--- /dev/null
+++ b/tools/keyboard-mouse-tester/index.html
@@ -0,0 +1,421 @@
+
+
+
+
+
+
+
+
+
+
+
+ Keyboard & Mouse Tester
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/tools/keyboard-mouse-tester/js/custom-script.js b/tools/keyboard-mouse-tester/js/custom-script.js
new file mode 100644
index 00000000..7934caf8
--- /dev/null
+++ b/tools/keyboard-mouse-tester/js/custom-script.js
@@ -0,0 +1,434 @@
+$(document).ready(function () {
+ load();
+ $(document).on("keyup press", function (event) {
+ event.preventDefault();
+ var key = event.keyCode;
+ var key_pos = event.code;
+ if (key_pos == "NumpadEnter") {
+ $(".keyPos" + key_pos).removeClass("press");
+ $(".keyPos" + key_pos).addClass("active");
+ keyNameDisplay(KeyNamelist(key_pos));
+ } else if (key_pos == "ShiftRight") {
+ $(".keyPos" + key_pos).removeClass("press");
+ $(".keyPos" + key_pos).addClass("active");
+ keyNameDisplay(KeyNamelist(key_pos));
+ } else if (key_pos == "ControlRight") {
+ $(".keyPos" + key_pos).removeClass("press");
+ $(".keyPos" + key_pos).addClass("active");
+ keyNameDisplay(KeyNamelist(key_pos));
+ } else if (key_pos == "AltRight") {
+ $(".keyPos" + key_pos).removeClass("press");
+ $(".keyPos" + key_pos).addClass("active");
+ keyNameDisplay(KeyNamelist(key_pos));
+ } else {
+ $(".key" + key).removeClass("press");
+ $(".key" + key).addClass("active");
+ keyNameDisplay(KeyNamelist(key));
+ }
+ });
+ $(document).on("keydown", function (event) {
+ event.preventDefault();
+ var key = event.keyCode;
+ var key_pos = event.code;
+ if (key_pos == "NumpadEnter") {
+ $(".keyPos" + key_pos).removeClass("active");
+ $(".keyPos" + key_pos).addClass("press");
+ } else if (key_pos == "ShiftRight") {
+ $(".keyPos" + key_pos).removeClass("active");
+ $(".keyPos" + key_pos).addClass("press");
+ } else if (key_pos == "ControlRight") {
+ $(".keyPos" + key_pos).removeClass("active");
+ $(".keyPos" + key_pos).addClass("press");
+ } else if (key_pos == "AltRight") {
+ $(".keyPos" + key_pos).removeClass("active");
+ $(".keyPos" + key_pos).addClass("press");
+ } else {
+ $(".key" + key).removeClass("active");
+ $(".key" + key).addClass("press");
+ }
+ });
+ $(document).on("mouseup", function (event) {
+ event.preventDefault();
+ var key = event.button;
+ $(".key" + key).removeClass("press");
+ $(".key" + key).addClass("active");
+ keyNameDisplay(KeyNamelist(key));
+ });
+ $(document).on("mousedown", function (event) {
+ event.preventDefault();
+ var key = event.button;
+ $(".key" + key).removeClass("active");
+ $(".key" + key).addClass("press");
+ });
+
+ $(document).bind("contextmenu", function (event) {
+ return false;
+ });
+
+ $(document).mousemove(function (event) {
+ $("x").text(event.pageX + ", " + event.pageY);
+ });
+
+ $(document).keydown(function (event) {
+ event.preventDefault();
+ var key1 = event.code;
+ $("y").text(key1);
+ });
+ });
+
+ $(window).on("wheel", function (event) {
+ event.preventDefault();
+ var delta = event.originalEvent.deltaY;
+ if (delta > 0) {
+ $(".scrollDown").removeClass("active");
+ $(".scrollDown").addClass("press");
+ $(".scrollDown").removeClass("press");
+ $(".scrollDown").addClass("active");
+ } else {
+ $(".scrollUp").removeClass("active");
+ $(".scrollUp").addClass("press");
+ $(".scrollUp").removeClass("press");
+ $(".scrollUp").addClass("active");
+ }
+ });
+
+ function keyNameDisplay(keyName) {
+ var str =
+ ' ";
+ $(".keyboard-header").prepend(str);
+ }
+ function load() {
+ Swal.fire({
+ title: "Loading...",
+ html:
+ ' Online Keyboard & Mouse Tester',
+ timer: 1000,
+ timerProgressBar: true,
+ showConfirmButton: false,
+ });
+ }
+ function KeyNamelist(keyCode) {
+ switch (keyCode) {
+ case "NumpadEnter":
+ return "Numpad Enter";
+ break;
+ case "ShiftRight":
+ return "Shift Right";
+ break;
+ case "ControlRight":
+ return "CTRL Right";
+ break;
+ case "AltRight":
+ return "ALT Right";
+ break;
+ case 27:
+ return "ESC";
+ break;
+ case 112:
+ return "F1";
+ break;
+ case 113:
+ return "F2";
+ break;
+ case 114:
+ return "F3";
+ break;
+ case 115:
+ return "F4";
+ break;
+ case 116:
+ return "F5";
+ break;
+ case 117:
+ return "F6";
+ break;
+ case 118:
+ return "F7";
+ break;
+ case 119:
+ return "F8";
+ break;
+ case 120:
+ return "F9";
+ break;
+ case 121:
+ return "F10";
+ break;
+ case 122:
+ return "F11";
+ break;
+ case 123:
+ return "F12";
+ break;
+ case 145:
+ return "Scr Lk";
+ break;
+ case 19:
+ return "Pause break";
+ break;
+ case 45:
+ return "ins";
+ break;
+ case 46:
+ return "del";
+ break;
+ case 36:
+ return "home";
+ break;
+ case 35:
+ return "end";
+ break;
+ case 33:
+ return "page up";
+ break;
+ case 34:
+ return "page down";
+ break;
+ case 192:
+ return "`";
+ break;
+ case 49:
+ return "1";
+ break;
+ case 50:
+ return "2";
+ break;
+ case 51:
+ return "3";
+ break;
+ case 52:
+ return "4";
+ break;
+ case 53:
+ return "5";
+ break;
+ case 54:
+ return "6";
+ break;
+ case 55:
+ return "7";
+ break;
+ case 56:
+ return "8";
+ break;
+ case 57:
+ return "9";
+ break;
+ case 48:
+ return "0";
+ break;
+ case 189:
+ return "-";
+ break;
+ case 187:
+ return "=";
+ break;
+ case 8:
+ return "backspace";
+ break;
+ case 144:
+ return "Numpad Lock";
+ break;
+ case 111:
+ return "Numpad /";
+ break;
+ case 106:
+ return "Numpad *";
+ break;
+ case 109:
+ return "Numpad -";
+ break;
+ case 9:
+ return "tab";
+ break;
+ case 81:
+ return "Q";
+ break;
+ case 87:
+ return "W";
+ break;
+ case 69:
+ return "E";
+ break;
+ case 82:
+ return "R";
+ break;
+ case 84:
+ return "T";
+ break;
+ case 89:
+ return "Y";
+ break;
+ case 85:
+ return "U";
+ break;
+ case 73:
+ return "I";
+ break;
+ case 79:
+ return "O";
+ break;
+ case 80:
+ return "P";
+ break;
+ case 219:
+ return "[";
+ break;
+ case 221:
+ return "]";
+ break;
+ case 220:
+ return "\\";
+ break;
+ case 103:
+ return "Numpad 7";
+ break;
+ case 104:
+ return "Numpad 8";
+ break;
+ case 105:
+ return "Numpad 9";
+ break;
+ case 107:
+ return "Numpad +";
+ break;
+ case 20:
+ return "Caps Lock";
+ break;
+ case 65:
+ return "A";
+ break;
+ case 83:
+ return "S";
+ break;
+ case 68:
+ return "D";
+ break;
+ case 70:
+ return "F";
+ break;
+ case 71:
+ return "G";
+ break;
+ case 72:
+ return "H";
+ break;
+ case 74:
+ return "J";
+ break;
+ case 75:
+ return "K";
+ break;
+ case 76:
+ return "L";
+ break;
+ case 59:
+ return ";:";
+ break;
+ case 186:
+ return ";";
+ break;
+ case 100:
+ return "Numpad 4";
+ break;
+ case 101:
+ return "Numpad 5";
+ break;
+ case 102:
+ return "Numpad 6";
+ break;
+ case 90:
+ return "Z";
+ break;
+ case 88:
+ return "X";
+ break;
+ case 67:
+ return "C";
+ break;
+ case 86:
+ return "V";
+ break;
+ case 66:
+ return "B";
+ break;
+ case 78:
+ return "N";
+ break;
+ case 77:
+ return "M";
+ break;
+ case 188:
+ return ",<";
+ break;
+ case 190:
+ return ".>";
+ break;
+ case 191:
+ return "/?";
+ break;
+ case 96:
+ return "Numpad 0";
+ break;
+ case 32:
+ return "Space";
+ break;
+ case 93:
+ return "menu";
+ break;
+ case 38:
+ return "\u2191";
+ break;
+ case 40:
+ return "\u2193";
+ break;
+ case 37:
+ return "\u2190";
+ break;
+ case 39:
+ return "\u2192";
+ break;
+ case 110:
+ return "Numpad .";
+ break;
+ case 97:
+ return "Numpad 1";
+ break;
+ case 98:
+ return "Numpad 2";
+ break;
+ case 99:
+ return "Numpad 3";
+ break;
+ case 0:
+ return "Left Click";
+ break;
+ case 1:
+ return "Middle Click";
+ break;
+ case 2:
+ return "Right Click";
+ break;
+ case 16:
+ return "Shift Left";
+ break;
+ case 18:
+ return "ALT Left";
+ break;
+ case 17:
+ return "CTRL left";
+ break;
+ case 91:
+ return "WIN";
+ break;
+ case 13:
+ return "Enter";
+ break;
+ case 44:
+ return "Prt Sc";
+ break;
+ }
+ }
+
\ No newline at end of file
diff --git a/tools/keyboard-mouse-tester/js/sweetalert2.min.js b/tools/keyboard-mouse-tester/js/sweetalert2.min.js
new file mode 100644
index 00000000..06ca81e7
--- /dev/null
+++ b/tools/keyboard-mouse-tester/js/sweetalert2.min.js
@@ -0,0 +1 @@
+!function(t,e){"object"==typeof exports&&"undefined"!=typeof module?module.exports=e():"function"==typeof define&&define.amd?define(e):(t=t||self).Sweetalert2=e()}(this,function(){"use strict";function r(t){return(r="function"==typeof Symbol&&"symbol"==typeof Symbol.iterator?function(t){return typeof t}:function(t){return t&&"function"==typeof Symbol&&t.constructor===Symbol&&t!==Symbol.prototype?"symbol":typeof t})(t)}function a(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}function o(t,e){for(var n=0;nt.clientHeight)}function lt(t){var e=window.getComputedStyle(t),n=parseFloat(e.getPropertyValue("animation-duration")||"0"),o=parseFloat(e.getPropertyValue("transition-duration")||"0");return 0