Reputation: 79
I am doing a rock, paper and scissors exercise and I just added a form with an input text and an input button to store the user name and show it on the DOM.
The thing is, with console.log($userName.value) it will only show me the value when it is on the box, if I delete it or submit it will show nothing or undefined, I added the form.submit() because I want the user to send the text on the input and then let the input empty (I also tried to set the .value to an empty string but it won't work either way.
I added it to a variable with innerHTML to show it on the DOM but if I clear the input it will show undefined.
I am probably skipping a few steps but I don't know how to get to it. Any guidance would be appreciated.
// Global DOM variables
const $selectBtn = document.querySelectorAll("[data-selector]");
const $displayUserScore = document.querySelector("#user-score");
const $displayComputerScore = document.querySelector("#computer-score")
const $showScore = document.querySelector("h5");
const $theWinnerIs = document.querySelector('#result-winner');
const $refreshBtnContainer = document.querySelector('#refresh-button-container');
const $icons = ["🪨", "🧻", "✂️"];
let $userForm = document.querySelector('#user-form');
let $userName = document.querySelector('#user-name');
// Score vaiables
const choices = ["rock", "paper", "scissors"];
let userScore = 0;
let computerScore = 0;
$userForm.addEventListener('submit', (event) => {
$newUserName = $userName.value;
$userForm.submit();
})
// For each button of buttons...
$selectBtn.forEach(function(button){
button.addEventListener("click", function() {
let computerOption = computerRandom() // Store random computer play on var
const userOption = button.dataset.selector; // userOption is equal to data-selector attribute
// Invoke functions plays the game and shows final winner.
playGame(userOption, computerOption);
theWinner();
// Add function with results
function playGame(userOption, computerOption) {
if (userOption === "rock") {
if (computerOption === "scissors") {
userScore++;
$displayUserScore.innerHTML = userScore;
$showScore.innerHTML = "The machine chooses "+"<span class=\"icon\">" + $icons[2] + "</span>" + ", you BEAT him!";
} else if (computerOption === "paper") {
computerScore++;
$displayComputerScore.innerHTML = computerScore;
$showScore.innerHTML = "The machine chooses "+"<span class=\"icon\">" + $icons[1] + "</span>" + ", you LOSE!";
} else if (userOption === computerOption) {
$showScore.innerHTML = "Draw!";
}
}
if (userOption === "paper") {
if (computerOption === "rock") {
userScore++;
$displayUserScore.innerHTML = userScore;
$showScore.innerHTML = "The machine chooses "+"<span class=\"icon\">" + $icons[0] + "</span>" + ", you BEAT him!";
} else if (computerOption === "scissors") {
computerScore++;
$displayComputerScore.innerHTML = computerScore;
$showScore.innerHTML = "The machine chooses "+"<span class=\"icon\">" + $icons[2] + "</span>" + ", you LOSE!";
} else if (userOption === computerOption) {
$showScore.innerHTML = "Draw!";
}
}
if (userOption === "scissors") {
if (computerOption === "paper") {
userScore++;
$displayUserScore.innerHTML = userScore;
$showScore.innerHTML = "The machine chooses "+"<span class=\"icon\">" + $icons[1] + "</span>" + ", you BEAT him!";
} else if (computerOption === "rock") {
computerScore++;
$displayComputerScore.innerHTML = computerScore;
$showScore.innerHTML = "The machine chooses "+"<span class=\"icon\">" + $icons[0] + "</span>" + ", you LOSE!";
} else if (userOption === computerOption) {
$showScore.innerHTML = "Draw!";
}
}
}
// Add a winners text function
function theWinner() {
if (userScore === 5) {
$theWinnerIs.innerHTML = $userName.value;
} else if (computerScore === 5) {
$theWinnerIs.innerHTML = "The machine!";
}
}
if (userScore === 5 || computerScore === 5) {
const $refreshBtn = document.createElement('button');
$refreshBtn.appendChild(document.createTextNode("Play again!"));
$refreshBtn.className = "refresh-btn";
$refreshBtnContainer.appendChild($refreshBtn);
let len = $selectBtn.length;
for (let i = 0; i < len; i++) {
$selectBtn[i].disabled = true;
}
$refreshBtn.addEventListener('click', () => {
userScore = 0;
computerScore = 0;
$displayUserScore.innerHTML = userScore;
$displayComputerScore.innerHTML = computerScore;
$showScore.innerHTML = "";
$theWinnerIs.innerHTML = "";
$refreshBtnContainer.innerHTML= "";
for (let i = 0; i < len; i++) {
$selectBtn[i].disabled = false;
}
})
}
})
})
// Random computer choice
function computerRandom () {
const randomNumber = Math.floor(Math.random() * choices.length);
return choices[randomNumber];
}
body {
box-sizing: border-box;
}
#container {
text-align: center;
margin-top: 5%;
}
h2 {
color:rebeccapurple;
font-size: 30px;
letter-spacing: 4px;
font-style: italic;
}
#user-name {
margin-bottom: 4em;
border-radius: 10px;
padding: .6em;
outline: none;
border: none;
}
#submit-name {
padding: .6em;
margin-left: .5em;
background: rebeccapurple;
border-radius: 10px;
border: none;
outline: none;
}
.btn-selector {
font-size: 4em;
background: rebeccapurple;
margin: .1em;
padding: .2em;
outline: none;
border: none;
cursor: pointer;
border-radius: 20%;
transition: 150ms;
}
.btn-selector:hover {
transform: scale(1.2);
}
#results {
display: flex;
justify-content: center;
}
.score {
margin-right: 1em;
font-size: 11px;
font-style: italic;
}
h3 {
color: rebeccapurple;
font-style: italic;
display: flex;
justify-content: center;
}
h5 {
margin-top: 7px;
color: olive;
font-size: 20px;
letter-spacing: 3px;
}
.icon {
font-size: 3em;
}
.refresh-btn {
padding: .8em;
background: rebeccapurple;
font-size: 30px;
font-style: bold;
border-radius: 20px;
border: none;
}
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Rock, paper and scissors</title>
<link rel="stylesheet" href="style.css">
<script src="script.js" defer></script>
</head>
<body>
<div id="container">
<h2>What is your name?</h2>
<form id ="user-form">
<input type="text" id="user-name" placeholder="Please, insert your name..">
<input type="submit" id="submit-name" value="Enviar">
</form>
<button class="btn-selector" data-selector="rock">🪨</button>
<button class="btn-selector" data-selector="paper">🧻</button>
<button class="btn-selector" data-selector="scissors">✂️</button>
<div id="results">
<h4>You: <span id="user-score" class="score" data-user-score>0</span></h4>
<h4>Computer: <span id="computer-score" class="score" data-computer-score>0</span></h4>
</div>
<h5></h5>
<div>
<h3>And the winner is...</h3>
<h3 id="result-winner"></h3>
</div>
<div id="refresh-button-container">
</div>
</div>
</body>
</html>
Thanks a lot.
Upvotes: 0
Views: 832
Reputation: 44086
There are few things you should be aware of when you have a <form>
and you register it to the "submit" event.
<form>
is to gather all values of all form controls that are:
<form>
itself<form>
via the form
attribute.name
attribute with a valid value. (excluding buttons)<input>
<form id="X">
)
<button>OK</button>
<button type='submit'>OK</button>
<input type='submit'>
<input type='image' src='https://loremflickr.com/48/24'>
<form id="X">
)
<button form="X">OK</button>
<button type='submit' form="X">OK</button>
<input type='submit' form="X">
<input type='image' src='https://loremflickr.com/48/24' form="X">
Not using a server, I assume that the behavior previously mentioned is undesirable. If so, event.preventDefault()
is needed (see Example A)
Define or declare a variable outside of the function, but within scope. Within scope in this context would just require that the variable be in the "vicinity" of the function to keep things simple see Figure III.
Figure III
let playerName = '';
function eventHandler(event) {//...
let playerName = '';
function eventHandler(event) {
// Stop the form from sending to a server
event.preventDefault();
// Reference all form controls
const IO = this.elements;
// Assign value to variable outside of function
playerName = IO.username.value;
// Clear input
IO.username.value = '';
console.log(playerName);
}
document.forms.rps.onsubmit = eventHandler;
<form id='rps'>
<fieldset>
<legend>Enter Name</legend>
<input id='username' name='username'><button>OK</button>
</fieldset>
</form>
The function and everything within the function gets garbage collected, but because you've created a closure by assigning a value from inside a function to a variable outside of the function, that value still resides within the variable after the function terminates. To verify, enter something and submit it. There should be a log entered in the console with the value of whatever you entered. That's during the run of the function, so to really be sure, right-click on the snippet directly and click "inspect", and click the "console" tab. Enter: console.log(playerName)
in the console. (See Appendix on Dev Tools)
<input>
Another way to save values is by using a hidden <input>
. The saved value will persist until the page is unloaded or the <input>
's value is reassigned. (see Example B). There are many ways to hide an <input>
and there basically 2 types of hidden:
Visibly Hidden <input>
<input>
, but as far as the browser and the DOM is concerned nothing special about said <input>
. It takes up space and it is within the layout.opacity
and visibility
hide tags this way. Some hacky ways include, color
and background
having the same color value or setting lengths to 0 like width
, height
, font-size
, etc. HTML attributes hidden
and attribute/value type="hidden"
are slightly different in that the latter will be included in a collection during a "submit" event.display: none
<input>
, nor does it occupy space in the layout. The DOM and browser still "sees" it and access it by normal means. If the <input>
was made visible by display:
"AnythingButNone" it would pop into existence amid other tags and probably cause unsightly shifting. So this form of hiding is best used for tags you don't plan on making visible.Since the only reason to use a hidden <input>
is to store a value display: none
will be the best choice. (see Example B).
function eventHandler(event) {
// Stop the form from sending to a server
event.preventDefault();
// Reference all form controls
const IO = this.elements;
// Assign the value of #username to #player
IO.player.value = IO.username.value;
// Clear input
IO.username.value = '';
console.log(IO.player.value);
}
document.forms.rps.onsubmit = eventHandler;
<form id='rps'>
<fieldset>
<legend>Enter Name</legend>
<input id='username' name='username'><button>OK</button>
</fieldset>
<input id='player' style='display: none'>
</form>
DevTools
Upvotes: 0
Reputation: 298
Not sure if your form will be sent, at least I don't think so.
If you want to display the name of the user or even store this data somewhere to display it somewhere you can do it this way
HTML code
<form id ="user-form">
<input type="text" id="user-name" placeholder="Please, insert your name.." onchange="registerInput(this);">
<input type="submit" id="submit-name" value="Enviar">
</form>
<h1>
</h1>
JavaScript code
// Here we initialize a global variable
var playerUsername = ""
let $userForm = document.querySelector('#user-form');
let $userName = document.querySelector('#user-name');
function registerInput(e)
{
const value = e.value;
// We assign the value of the input to playerUsername
// So we can access it globally
playerUsername = value;
}
$userForm.addEventListener('submit', (event) => {
event.preventDefault();
// Here we show the user
document.querySelector('h1').innerText = 'Hello : ' + inputValue;
// Now let's remove the value of the input
// We put an empty string
$userName.innerValue = ""
// Well done !
})
Link : https://jsfiddle.net/k49bgu0c/6/
In case you change the .html page you will lose access to this variable, so how to do in this case?
For that you can store the result of your input in the localStorage, this one will allow you to access to the data you have inserted inside, I let you read about the localStorage and how it works
Upvotes: 1
Reputation: 782564
Use a different variable in the function. There you can use the $userName
global variable to access the HTML element, and .value
to get its value.
let $userForm = document.querySelector('#user-form');
let $userName = document.querySelector('#user-name');
$userForm.addEventListener('submit', (event) => {
const name = $userName.value;
console.log(name);
$userForm.submit();
})
<form id="user-form">
<input type="text" id="user-name" placeholder="Please, insert your name..">
<input type="submit" id="submit-name" value="Enviar">
</form>
Upvotes: 2