Beispiel:Lotto-4.html
Aus SELFHTML-Wiki
<!doctype html>
<html>
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<link rel="stylesheet" media="screen" href="./Beispiel:SELFHTML-Beispiel-Grundlayout.css">
<title>Lotto - 6 aus 49</title>
<style>
.lotto input {
position: absolute !important;
clip: rect(1px, 1px, 1px, 1px);
padding:0 !important;
border:0 !important;
height: 1px !important;
width: 1px !important;
overflow: hidden;
}
.lotto label {
position: relative;
text-align: center;
color: firebrick;
border: thin solid firebrick;
line-height: 1.5;
}
.lotto :checked + label::after {
content: "×";
position: absolute;
left: -0.35rem;
top: -1.25rem;
right: 0;
font-size: 2.5rem;
color: darkblue;
opacity: .6;
}
.lotto fieldset {
display: grid;
gap: .25rem;
width: min-content;
}
.lotto fieldset:first-of-type {
grid-template: repeat(7, 1.5rem) / repeat(7, 1.5rem);
}
.lotto fieldset:last-of-type {
grid-template: 1.5rem / repeat(10, 1.5rem);
}
.lotto .error,
.lotto .success {
padding: 1rem 2rem;
}
.lotto .error {
background: #ffdddd;
color: red;
}
.lotto .success {
background: #ddffdd;
color: green;
}
</style>
<script>
class Lotto {
/**
* display alerts to the user
*/
alert (text, type) {
if (text) {
setTimeout(
() => {
this.alerts.textContent = text;
this.alerts.className = (type ? type : "error");
},
50
);
} else {
// reset
this.alerts.textContent = "";
this.alerts.className = "";
}
}
/**
* GUI element (<p>)
*/
alerts = document.createElement("p");
/**
* setup
*/
constructor () {
this.createGUI();
document.addEventListener("change", e => { this.handleChange(e); });
document.addEventListener("click", e => { this.handleClick(e); });
// polyfill for native Array.shuffle method
if (!Array.prototype.shuffle) {
// source: https://medium.com/@nitinpatel_20236/-15ea3f84bfb
Array.prototype.shuffle = function () {
const a = this;
var i = a.length - 1;
while (i > 0) {
const j = Math.floor(Math.random() * i);
const temp = a[i];
a[i] = a[j];
a[j] = temp;
i--;
}
return a;
};
}
}
/**
* GUI container (<form>)
*/
container = document.createElement("form");
/**
* create complete GUI
*/
createGUI () {
// container
this.container.classList.add("lotto");
document.body.appendChild(this.container);
// selection n out of m
const nm = this.container.appendChild(
document.createElement("fieldset")
);
nm.appendChild(document.createElement("legend"));
nm.lastChild.textContent = "6 aus 49";
for (var i = 1; i <= this.selection.m; i++) {
// <input type="checkbox" id="i23">
nm.appendChild(document.createElement("input"));
nm.lastChild.id = "i"+i;
nm.lastChild.type = "checkbox";
// <label for="i23">23</label>
nm.appendChild(document.createElement("label"));
nm.lastChild.htmlFor = "i"+i;
nm.lastChild.textContent = i;
}
// additional selection 1 out of 10
// selection n out of m
const s = this.container.appendChild(
document.createElement("fieldset")
);
s.appendChild(document.createElement("legend"));
s.lastChild.textContent = "Superzahl";
for (var i = 1; i < 11; i++) {
// <input type="checkbox" id="s10">
s.appendChild(document.createElement("input"));
s.lastChild.id = "s"+i;
s.lastChild.name = "s";
s.lastChild.type = "radio";
if (1 == i) {
s.lastChild.setAttribute("checked", "checked");
}
// <label for="s10">10</label>
s.appendChild(document.createElement("label"));
s.lastChild.htmlFor = "s"+i;
s.lastChild.textContent = i;
}
// button
const b = this.container.appendChild(
document.createElement("p")
);
b.appendChild(document.createElement("button"));
b.lastChild.textContent = "Ziehung starten!";
b.lastChild.type = "button";
// alerts
this.container.appendChild(this.alerts);
}
/**
* react to change events
*
* @param Object
*/
handleChange (e) {
const nm = this.container.querySelectorAll('[id^="i"]:checked');
// reset alerts
this.alert();
// are we inside limits?
if (nm.length > this.selection.n) {
// revert last change
e.target.click();
this.alert(
[
"Sie können maximal",
this.selection.n,
"Zahlen für die Ziehung auswählen!"
].join(" ")
);
}
}
/**
* react to click events
*
* @param Object
*/
handleClick (e) {
if (this.container.querySelector("button") == e.target) {
// check required number of selections
const
nm = this.container.querySelectorAll('[id^="i"]:checked'),
s = this.container.querySelectorAll('[id^="s"]:checked');
var errors = [];
// reset alerts
this.alert();
if (nm.length < this.selection.n) {
errors.push(
[
"Sie benötigen",
this.selection.n,
"Zahlen für die Ziehung!"
].join(" ")
);
}
if (!s.length) {
errors.push(
"Sie haben noch keine Superzahl ausgewählt!"
);
}
if (errors.length) {
this.alert(errors.join(" - "));
} else {
this.alert(
[
"Lottozahlen:",
this.pick_n_outOf_m(
this.selection.n,
this.selection.m
),
" - Superzahl:",
this.pick_n_outOf_m(1, 10)
].join(" "),
"success"
);
}
}
}
/**
* selection size
*
* @param Object
*/
selection = { n: 6, m: 49 };
/**
* pick n from a pool of numbers ranged from 1 to m
*
* @param int
* @param int
*/
pick_n_outOf_m (size, highestNumber) {
const pool = Array(highestNumber)
.fill() // damit map() so gelingt
.map((_, i) => i + size) // Werte von n-m eintragen
.shuffle();
const pick = pool.slice(0, size);
pick.sort();
return pick;
}
}
document.addEventListener('DOMContentLoaded', () => {
new Lotto();
});
</script>
</head>
<body>
<h1>Lotto – 6 aus 49</h1>
<p class="warnung">Glücksspiel kann süchtig machen.</p>
</body>
</html>