Mohamed Khalaf
Mohamed Khalaf

Reputation: 3

Span isn't updated when I delete the contents of my input field

I want to link a <span> element's content to the value of an input field, but it stops working after it runs the first time.

I want to automatically validate the contents of the input field before I send it to the server.

function valid() {
  var username = document.getElementById('name').value;
  var refusesymbol = ['<', '>', '@', '.', ',', '\"', '\'', '\?', '\\', '\/', '\*', '\+', '\-', '\-', '\_', '(', ')', '{', '}', '$', '#', '!', '^', '&', '|', '~', , '\;'];

  for (var i = 0; i < refusesymbol.length; i++) {
    if (username.includes(refusesymbol[i])) {
      document.getElementById('sname').innerHTML = "invalid";
      return false;
    } else {
      document.getElementById('sname').innerHRTML = "valid";
    }

  }
}
<form method="POST" action="regist.php" enctype="multipart/form-data" class="form">
  <label>USER NAME</label><br />
  <input type="text" name="name" id="name" autocomplete="off" onkeyup="valid()" /><br />
  <span id="sname" style="color: red;"></span><br />
</form>

This works once, but after that the value of span becomes fixed and no longer updates.

Upvotes: 0

Views: 55

Answers (3)

Professor Abronsius
Professor Abronsius

Reputation: 33813

As inline event handlers are no longer considered a good way of assigning an event listener typically one now uses addEventListener. The below code will update the value in the SPAN element with each keyup dependant upon the conditions within the anonymous callback function.

using Array.some(callback) means you can break out from the iteration when whatever condition is met inside the loop. This makes it ideal in this situation as the loop does not need to be finished before proceeding with other tasks - which should make it marginally quicker.

From MDN

The some() method tests whether at least one element in the array passes the test implemented by the provided function. It returns a Boolean value.

<!DOCTYPE html>
<html lang='en'>
    <head>
        <meta charset='utf-8' />
        <title>Form validation</title>
        <style>
            form > *{display:block;font-family:verdana}
            [name='name'] + span{width:30%;padding:1rem;text-transform:capitalize}
            .invalid{color:red!important;}
            .valid{color:green!important;}
        </style>
    </head>
    <body>
        <form method='post' action='regist.php' enctype='multipart/form-data' class='form'>
            <label>user name</label>
            <input type='text' name='name' autocomplete='off' />
            <span></span>
        </form>
        <script>

            let input=document.querySelector( 'input[ type="text" ][ name="name" ]' );
            let span=input.nextElementSibling;
            let style={ /* css classes & indicator text */
                good:'valid',
                bad:'invalid'
            }
            /*
                The input element will be monitored on every keyup and the
                contents of the SPAN element will alter with no further 
                interaction - it will be cleared if there is no text, marked 
                as invalid if there are bad characters and marked as valid if
                none detected...
            */
            input.addEventListener( 'keyup', function(){
                /* assign the value of the input element as a variable so that it can be easily referenced within the arrow function */
                let value=this.value;

                /* a list of bad characters which will invalidate data entry if detected */
                let bad=['<','>','@','.',',','\"','\'','\?','\\','\/','\*','\+','\-','\-','\_','(',')','{','}','$','#','!','^','&','|','~',,'\;'];

                /* if the field is empty then it is valid but should not be indicated as such */
                if( value=='' ){
                    span.innerText=value;
                    span.removeAttribute('class');
                    return;
                }

                /* iterate through the bad chars until one is found, then return true */
                let status=bad.some( char=>{
                    if( value.includes( char ) ){
                        span.innerText=span.className=style.bad;
                        return true;
                    }
                });

                /* if no bad chars are found, indicate field as valid */
                if( !status ){
                    span.innerText=span.className=style.good;
                }
            });
        </script>
    </body>
</html>

Upvotes: 0

Alamgir Ahamed saif
Alamgir Ahamed saif

Reputation: 3

Write:

document.getElementById('sname').innerHTML="valid";

Instead of:

document.getElementById('sname').innerHRTML="valid";

Upvotes: 0

daddygames
daddygames

Reputation: 1928

The for loop was not closed properly.

innerHRTML is invalid syntax.

Here is updated version of your code JavaScript:

function valid(){ 
    document.getElementById('sname').innerHTML = ''; // reset this on key stroke
    var username=document.getElementById('name').value;
    var refusesymbol= 
        ['<','>','@','.',',','\"','\'','\?','\\','\/','\*','\+','\-','\-','\_','(',')','{','}','$','#','!','^','&','|','~',,'\;'];
    for(var i=0;i<refusesymbol.length;i++)
            {
        if(username.includes(refusesymbol[i]))
        {
            document.getElementById('sname').innerHTML="invalid";
            return false;
        }
        else
        {
          document.getElementById('sname').innerHTML="valid"; // invalid syntax was here
        }
    } // this was missing
}

Upvotes: 1

Related Questions